How to Display 1 Column sum in other Column - mysql

I have a table that has different columns display different values.
I need to add a new column that displays sum of 1 column in each row of other column.
This is what i need to display.
I have written following query but its only displaying 1 in each row of last column.
select inStation.name TapInStation , outStation.name TapOutStation,
count(trx.passengerCount) PassengerCount, sum(trx.amount) Fare,
(select sum(passengerCount) from transactions iTrx
where iTrx.ID = trx.ID) PassengerPercent
from transactions trx
inner join
station inStation on inStation.ID = trx.fromStation
inner join
station outStation on outStation.ID = trx.toStation
GROUP BY
TapInStation, TapOutStation

If you want the total, then remove the correlation clause. This may do what you want:
select inStation.name as TapInStation , outStation.name as TapOutStation,
count(trx.passengerCount) as PassengerCount,
sum(trx.amount) as Fare,
(select sum(passengerCount) from transactions iTrx) as PassengerPercent
I'm not sure why you would called the "total" something like PassengerPercent, but this should return the overall total.
I also suspect that you might want a sum() for the previous expression.

Related

MYSQL GROUP BY on 2 Tables with MAX

I have 2 mysql tables:
record table:
and
race table:
I want to select the records from the 1st table group by id_Race but only the MAX from column "secs".
I tried the following but didnt work:
$query = "SELECT rec.RecordsID,rec.id_Athlete,rec.date_record,rec.id_Race,rec.placeevent,rec.mins,rec.secs,rec.huns,rec.distance,rec.records_text,r.name,MAX(rec.secs)
FROM records AS rec INNER JOIN race AS r ON r.RaceID=rec.id_Race WHERE (id_Athlete=$u_athlete) GROUP BY rec.id_Race;";
($u_athlete is a variable i get from _SESSION)
Can you help me about that?
Thank you.
When you use an aggregation function like MAX and select all fields, you are forced to include all selected fields that are not affected by the MAX inside the GROUP BY clause.
Though you can use a window function like ROW_NUMBER that will group by specifically on id_Race and order by the secs column in a descendent way (so that the highest value of secs will be associated with row_number=1).
Afterwards you can select the rows which have row_number=1 and the id_Athlete you pass using the variable.
SELECT
rec.RecordsID,
rec.id_Athlete,
rec.date_record,
rec.id_Race,
rec.placeevent,
rec.mins,
rec.secs,
rec.huns,
rec.distance,
rec.records_text,
race.name,
FROM
(
SELECT
*,
ROW_NUMBER() OVER(PARTITION BY id_race ORDER BY secs) rank
FROM
record
) rec
INNER JOIN
race race
ON
race.RaceID=rec.id_Race
WHERE
rec.rank = 1
AND
rec.id_Athlete = $u_athlete;

group by id in descending order in select statement

I have MySQL statement where I'm trying to select distinct rows with the latest date.
This is the SQL statement:
SELECT st.seno, tc.pl, tc.sno, st.val1, st.val2, st.date
FROM tc
LEFT JOIN st ON tc.seno = st.seno AND tc.pl = st.pl AND st.seno = 1304239136
WHERE tc.pl = 1
ORDER BY st.date DESC
This is the data returned:
I want to distinct by unique 'tc.sno', therefore I only want the first and third row returned as the middle date is earlier then the top one for the 'sno' 3. The 'sno' could always be different so I do not want to hardcode those numbers. I was trying to use 'GROUP BY' but it just picks the first value of the date, tried using 'HAVING' and combining select statements together but can't seem to get it working. (the val1 and val2 in row 2 could be random it is just a coincidence that they exact in this example)

MySQL SELECT query that counts left joined rows takes too long

Does anyone know how to optimize this query?
SELECT planbook.*,
COUNT(pb_unit_id) AS total_units,
COUNT(pb_lsn_id) AS total_lessons
FROM planbook
LEFT JOIN planbook_unit ON pb_unit_pb_id = pb_id
LEFT JOIN planbook_lesson ON pb_lsn_pb_id = pb_id
WHERE pb_site_id = 1
GROUP BY pb_id
The slow part is getting the total number of matching units and lessons. I have indexes on the following fields (and others):
planbook.pb_id
planbook_unit.pb_unit_pb_id
planbook_lesson.pb_lsn_pb_id
My only objective is to get the total number of matching units and lessons along with the details of each planbook row.
However, this query is taking around 35 seconds. I have 1625 records in planbook, 13,693 records in planbook_unit, and 122,950 records in planbook_lesson.
Any suggestions?
Edit: Explain Results
SELECT planbook.*,
( SELECT COUNT(*) FROM planbook_unit
WHERE pb_unit_pb_id = planbook.pb_id ) AS total_units,
( SELECT COUNT(*) FROM planbook_lesson
WHERE pb_lsn_pb_id = planbook.pb_id ) AS total_lessons
FROM planbook
WHERE pb_site_id = 1
planbook: INDEX(pb_site_id)
planbook_unit: INDEX(pb_unit_pb_id)
planbook_lesson: INDEX(pb_lsn_pb_id)
Looking to your query
You should add and index for
table planbook column pb_site_id
and eventually a composite one for
table planbook column (pb_site_id, pd_id)

Should MAX in Group By Retrieve the Whole Row Data

I have a bunch of sql columns to retrieve. This is my SQL statement:
SELECT b.iposx_model_id,
a.mrModel, MAX(a.mrRevision) as mrRevision, a.mrApprovedBy, ...
FROM mydb1.tbl_model_revision a
INNER JOIN mydb2.model_from_revision_process b
ON b.mrModel = a.mrModel
WHERE a.mrType = 1
GROUP BY a.mrModel
ORDER BY b.iposx_model_id ASC
On a certain mrModel column taht I retrieved, these are the data that I'm querying for:
In my query, it states that I should get the data with the Max mrRevision which corresponds to the third row.
However, upon running the sql statement, I got the max mrRevision which is 2, coming from the third row. But the other column data I get came from the 2nd row, an example is mrApprovedBy which is 1035 instead of 10. Why is that happening?
The use group by for only a part of the column not involved in aggegation function is select clause
is depreacted in SQL because where work produce unpredicatble result
In most DB and in the most recent version of mysql this use of group by is not allowed
for obtain the row corresponding to the max value you could use a join on the values that match the right content
SELECT
b.iposx_model_id
, a.mrModel
, t.mrRevision
, a.mrApprovedBy
, ...
FROM mydb1.tbl_model_revision a
JOIN (
select mrModel, MAX(mrRevision) as mrRevision
from mydb1.tbl_model_revision
GROUP BY a.mrModel
) t on a.mrModel = t.mrModel and a.mrRevision = t.mrRevision
JOIN mydb2.model_from_revision_process b ON b.mrModel = a.mrModel
WHERE a.mrType = 1
ORDER BY b.iposx_model_id ASC

Get number of rows returned by subquery along with the columns returned by subquery

I find it really annoying to be not able to get the number of rows without having to use group by. I just need to get the "Total count" that my subquery returned.
Here is what my subquery looks like:
select sales_flat_order.increment_id, sales_flat_order.created_at, sales_flat_order.status, dispatch.dispatch_date,
DATEDIFF(TO_DATE(dispatch.dispatch_date), TO_DATE(sales_flat_order.created_at)) as delay
FROM
magentodb.sales_flat_order
LEFT OUTER JOIN erpdb.dispatch
ON
sales_flat_order.increment_id == dispatch.order_num
where
TO_DATE(created_at) >= DATE_SUB(current_date(),6)
AND
TO_DATE(created_at) <= DATE_SUB(current_date(), 3)
AND
sales_flat_order.status NOT IN ('canceled', 'exchange', 'rto', 'pending_auth', 'pending_payment' ,'partial_refund','refund', 'refund_cash', 'partial_refund_cash', 'holded')
)
AS TempFiltered
Now, I add 1 extra WHERE clause in my outer query so that it returned "lesser" number of rows, let's call this column y .
I then require to take percentage of x to y(i.e number of rows returned by outer query to subquery)
I do not wan to repeat my subquery only to get count of the rows. HOw do I get it?
This is what I have so far: But ofcourse it is wrong. I can not get count of all my rows without having to exclude select columns or using them in group by. HOw do I resolve this?
SELECT tempfiltered.delay, count(*) as countOfOrders,(100*count(*))/tempfiltered.Total) over () as percentage
FROM
(
select count(*) as Total, sales_flat_order.increment_id, sales_flat_order.created_at, sales_flat_order.status, dispatch.dispatch_date,
DATEDIFF(TO_DATE(dispatch.dispatch_date), TO_DATE(sales_flat_order.created_at)) as delay
FROM
magentodb.sales_flat_order
LEFT OUTER JOIN erpdb.dispatch
ON
sales_flat_order.increment_id == dispatch.order_num
where
TO_DATE(created_at) >= DATE_SUB(current_date(),6)
AND
TO_DATE(created_at) <= DATE_SUB(current_date(), 3)
AND
sales_flat_order.status NOT IN ('canceled', 'exchange', 'rto', 'pending_auth', 'pending_payment' ,'partial_refund','refund', 'refund_cash', 'partial_refund_cash', 'holded')
)
AS TempFiltered
Where
DATEDIFF(TO_DATE(TempFiltered.dispatch_date), TO_DATE(TempFiltered.created_at)) > 1
GROUP BY tempfiltered.delay
ORDER BY tempfiltered.delay
You could change the subquery into a SELECT INTO query, and put the data in a temporary table, and use that in the main query, and separately just select count(*) of that temporary table. That should pretty much satisfy your requirement.