Sum multiple fields in 1 table - php

Hi I would like to sum my 4 columns in my table.
but I get error he SUM function requires 1 argument(s)
itemcost table
+------+------+------+------+------+
| id | col1 | col2 | col3 | col4 |
+======+======+======+======+======+
| 0002 | 5 | 5 | 5 | 5 |
+------+------+------+------+------+
| | | | | |
+------+------+------+------+------+
| | | | | |
+------+------+------+------+------+
$cost= DB::table('itemcost')
->select(
DB::raw('SUM(col1,col2,col3,col4) as unitprice')
);
Thank you in advance.

To sum just column of every single row, use:
(col1+col2+col3+col4) as unitprice
Or, to sum columns with rows, use:
(SUM(col1)+SUM(col2)+SUM(col3)+SUM(col4)) as unitprice
By the way, here is an article with examples

You could add columns with + sign,
Try like bellow:
$cost= DB::table('itemcost')
->select(
DB::raw('SUM(col1+col2+col3+col4) as unitprice')
);

Related

SQL query to return combined data of all rows that don't belong to current user

Imagine this is my table:
----------------------------------------------------
| id | user_id | amount_1 | amount_2 | amount_3 |
----------------------------------------------------
| 1 | 1 | 2 | 3 | 4 |
----------------------------------------------------
| 2 | 2 | 2 | 1 | 1 |
----------------------------------------------------
| 3 | 2 | 1 | 2 | 2 |
----------------------------------------------------
| 4 | 3 | 2 | 1 | 4 |
----------------------------------------------------
I need a query that gives me one result set for every entry that belongs to my current user, and then returns everything else as a single combined row with the amounts summed.
So in this case if I am user 1, I should get the following rows back:
---------------------------------------
| id | amount_1 | amount_2 | amount_3 |
---------------------------------------
| 1 | 2 | 3 | 4 | my own amounts
---------------------------------------
| 2 | 5 | 4 | 7 | everyone else's amounts
---------------------------------------
Any tips?
I've considered it might be a better idea to just filter the data in the code (php). Please help i'm starting to hate myself
You could use a UNION in sql
select 1 id, amount_1, amount_2, amount_3
from my_table
where user_id = 1
union
select 2 , sum(amount_1) , sum(amount_2), sum(amount_3 )
from my_table
where user_id <> 1
You can do with one query using union:
SELECT user_id, amount_1, amount_2, amount_3
FROM table
WHERE user_id = YOUR_USER_ID
UNION
SELECT -1, SUM(amount_1) AS amount_1, SUM(amount_2) AS amount_2, SUM(amount_3) AS amount_3
FROM table
WHERE user_id != YOUR_USER_ID
You can use aggregation in one fell swoop:
select (case when user_id = 1 then id end) as my_user_or_not,
sum(amount_1), sum(amount_2), sum(amount_3)
from t
group by my_user_or_not;
The null values in the first column indicate another user. You have labelled the column id, which is a bit problematic if you were -- for instance -- to choose user_id = 2 in your example. NULL seems safer for this purpose.

Laravel Query Builder - Sum Where and Sum Where

I have a table called stock_movements:
| product_id | type | qty |
|------------|------|------|
| 1 | A | 2 |
| 1 | A | 1 |
| 1 | A | 7 |
| 1 | B | -2 |
| 1 | B | -4 |
| 1 | B | -1 |
| 2 | A | 2 |
| 2 | A | 1 |
| 2 | A | 7 |
| 2 | B | -3 |
| 2 | B | -3 |
| 2 | B | -1 |
I am trying to create a collection of the products where which have the values of the sum of A and sum of B.
i.e.
Group by products, type
Sum qty for each type
The key thing is that it is a collection against the product, which is the bit I am struggling with. Does anyone have any advice?
So far I have got...
return $this->stockMovements()->groupBy('product_id')
->selectRaw('sum(qty), product_id')
->where('type', $this->type)
->get();
But this does not split out for types A and B.
You need a basic pivot query, which would look something like this in Laravel:
return $this->stockMovements()
->selectRaw("SUM(CASE WHEN type = 'A' THEN qty ELSE 0 END) AS sum_a, ".
"SUM(CASE WHEN type = 'B' THEN qty ELSE 0 END) AS sum_b, product_id")
->groupBy('product_id')
->get();
I removed the WHERE clause, because your data only seems to have two types, and there isn't much sense in restricting that. If you really want the sum of quantity for just A or B, then we can write a much simpler Laravel/MySQL query.
Using A Raw Expression
$result = DB::table('stock_movements')
->select(DB::raw('sum(qty) as sum_qty, type'))
->groupBy('type')
->get();
Rule of thumb for the use of aggregation functions in the SELECT clause.
If a select block does have a GROUP BY clause, any column
specification specified in the SELECT clause must exclusively occur as
a parameter of an aggregated function or in the list of columns given
in the GROUP BY clause, or in both.
For more details :
http://www.informit.com/articles/article.aspx?p=664143&seqNum=6

rank query in laravel from one table data

At the moment it gets the races times in order but i want to combined the user_id column together, but to make sure when it groups it together it, the fastest recorded_time is kept.
Example of what i have so far from the query
User_id | race_id | recorded_time | stroke |
__________________________________________
2 | 2 | 10.03 | fly |
____________________________________________
1 | 3 | 12.98 | fly |
____________________________________________
2 3 13.58 | fly |
Here is the code that gives me that result
$query->where('race_history.stroke', '=', $stroke)
->orderBy('recorded_time', 'ASC')->get();
This is what i want it to return
User_id | race_id | recorded_time | stroke |
__________________________________________
2 | 2 | 10.03 | fly |
____________________________________________
1 | 3 | 12.98 | fly |
____________________________________________
I have tried the code bellow but it doesn't take the fastest record time
$query->where('stroke', '=', $stroke)
->orderBy('recorded_time', 'ASC')
->groupBy('user_id')->get();
But Instead produces this
User_id | race_id | recorded_time | stroke |
__________________________________________
1 | 3 | 12.98 | fly |
____________________________________________
2 | 3 | 13.58 | fly |
____________________________________________
So its grouping it by user_id BUT not taking it fastest recorded time
I have tried so many ways anyone can help this is a raw query to get what i want i would use this but the AND distance doesnt like this..
$total = DB::select(DB::raw('
SELECT *, min(recorded_time) as time
FROM race_history
WHERE stroke = "' . $stroke . '" AND distance="' . $distance . '"
GROUP BY user_id
ORDER BY min(recorded_time) ASC
'));
Here's raw query as I don't know laravel syntax
SELECT `user_id`, `race_id`, min(`recorded_time`) AS `recorded_time`, `stroke`
FROM `race_history`
WHERE `stroke` = 'fly'
GROUP BY `user_id`
ORDER BY `recorded_time` ASC

How to bind string column data

I want to write a php script to compare rows from the database and then adds the values together if payment_id are matches. Based on payment_id:
Example:
+----+------------+-----------+--------+
| id | payment_id | cheque_id | amount |
+----+------------+-----------+--------+
| 1 | 1000 | MB101 | 20 |
| 2 | 1000 | MB102 | 20 |
| 3 | 1111 | MB113 | 20 |
+----+------------+-----------+--------+
Result required
+------+--------------+----+
| 1000 | MB101/MB102 | 40 |
| 1111 | MB113 | 20 |
+------+--------------+----+
Trying to merge cheque column as string. For 'Amount' column I know that should be use SUM.
Any suggestions is appreciated,
Thanks
use GROUP BY
select payment_id,group_concat(cheque_id SEPARATOR '/') as cheque_ids,
SUM(amount) as amount
FROM table name
GROUP BY payment_id
I found the solution
SELECT payment_id, group_concat(cheque_id SEPARATOR '/') AS cheque_ids,
SUM(amount) AS amount
FROM tbl_name
GROUP BY payment_id

find row from mysql table with multiple parameters (from different columns) using php

I have a mysql table as below:
--------------------
| Sl | col1 | col2 |
--------------------
| 1 | data1| msg1 |
--------------------
| 2 | data2| msg2 |
--------------------
| 3 | data1| msg3 |
--------------------
| 4 | data2| msg4 |
--------------------
| 5 | data1| msg5 |
--------------------
I have a php string $query = "select * from table WHERE col1='data1'"; , which fetch array 3 results (row number 1, 3, and 5). But i want to get a specific row containing "data1" in "col1" and "msg3" in "col2" (which is row number 3) in a single query. How can I make this possible?
Use AND in the WHERE clause to match multiple conditions:
SELECT * FROM table WHERE col1='data1' AND col2='msg3'

Categories