Avoiding redundant expressions in SELECT query - mysql

Is there any way to avoid repeating column expressions in the SELECT query? I want to divide the sum and count of a column but would like to use the assigned name instead of repeating SUM(value)/COUNT(value) or using a sub query. Is this possible? If so, does that speed up the query by not repeating the calculation of the sum and count or does mysql remember already calculated expressions?
SELECT datalist.type, SUM(value) AS type_sum, COUNT(value) AS type_count, type_sum/type_count
FROM (...) AS datalist
GROUP BY datalist.type
throws: #1054 - Unknown column 'type_sum' in field list

Unless you put it in outer query, this is the only way.
SELECT datalist.type, SUM(value) AS type_sum, COUNT(value) AS type_count, SUM(value)/COUNT(value)
FROM (...) AS datalist
GROUP BY datalist.type

One workaround would be to use a alias table with pre-defined calculations and then later call it from outer table such as:
select d.type_sum/d.type_count as dividedValue from (SELECT datalist.type, SUM(value)
AS type_sum, COUNT(value) AS type_count
FROM (...) )AS d
GROUP BY d.type

Related

Access: Use scalar correlated subquery result for sorting

In Access, is it possible to use the result of a scalar correlated subquery to sort the resultant rows? This didn't work (returned a sql error):
SELECT (SELECT MIN(DateTime) FROM Appt WHERE (PatientID = XXX.ID)) AS minDT, XXX.FullName,
FROM Patient AS XXX
ORDER BY minDT;
Replacing the "minDT" in the ORDER BY clause with the entire expression didn't work either.
Access won't allow you to use a field expression alias in the ORDER BY, but you can use a column's ordinal number ...
SELECT *
FROM
(
SELECT
(
SELECT MIN([DateTime])
FROM Appt
WHERE (PatientID = XXX.ID)
) AS minDT,
XXX.FullName
FROM Patient AS XXX
) AS sub
ORDER BY 1;
Note I bracketed the DateTime field name because I suspect it's a reserved word.
And don't include a comma after the last item in the SELECT field expression list.

mysql calculate percentage for diffrent groups

I want to calculate percentage for test groups.
I have group A,B and C. And I want to know how much success percentage each group have.
My first query is counting total test ran in each group by doing the following:
SELECT type, count(type) as total_runs
From mytable
Where ran_at > '2015-09-11'
Group by type
Second query is counting success for each group:
SELECT type, count(type) as success
FROM mytable
where run_status like '%success%' and ran_at> '2015-09-11'
Group by type
Now I need to divide one in the other and multiply in 100.
how do I do this in one query in an efficient way, I guess nested query is not so efficient- but anyway I can't see how I can uses nested query to solve it.
I would appreciate answer which include simple way, maybe not so efficient, and an efficient way with explanations
You can just use conditional aggregation:
SELECT type, sum(run_status like '%success%') as success,
100 * avg(run_status like '%success%') as p_success
FROM mytable
where ran_at> '2015-09-11'
Group by type;
In a numeric context, MySQL treats boolean expressions as integers with 1 for true and 0 for false. The above works assuming that run_status is not NULL. If it can be NULL, then you need an explicit case statement for the avg().
I had this one, but Gordon have a better solution if run_status is not NULL.
Select type, sum(if(run_status like '%success%',1,0)) / count(1) * 100) as p_success
From mytable
Where ran_at > '2015-09-11'
Group by type

Temporary Variable with aggregate field and group by doesn't work in mysql

I am trying to get cumulative value of a column using temporary variable.
SELECT sum(price), #temp := #temp + sum(price) AS cumulative_price FROM `table`, (SELECT #temp := 0) B GROUP BY item
It work when there is no group by and aggregate field. However, when there is group by field, value of cumulative_price is same as sum(price), which is not a expected.
What could be the reason of this inconsistency?
It should not work. According to Doc
In a SELECT statement, each select expression is evaluated only when
sent to the client. This means that in a HAVING, GROUP BY, or ORDER BY
clause, referring to a variable that is assigned a value in the select
expression list does not work as expected:
mysql> SELECT (#aa:=id) AS a, (#aa+3) AS b FROM tbl_name HAVING b=5;
The reference to b in the HAVING clause refers to an alias for an
expression in the select list that uses #aa. This does not work as
expected: #aa contains the value of id from the previous selected row,
not from the current row.
So when you define a variable it will work for current row not set of rows

Is it possible to sum a expression column in access?

I have a column in access I need to get the total of. When I try the below method in my query I get the error "You tried to execute a query that does not include the specified expression 'ID' as part of an aggregate function."
Expr1: Sum([Column1])
Edit my query:
SELECT tblTest.ID,Field1,Sum([Field1]) AS Expr1 From tblTest;
Your question needs more details but I think you want this:
SELECT Sum(yourColumn)
FROM yourTable
Then if you need to you will have to add a GROUP BY
SELECT Sum(yourColumn)
FROM yourTable
GROUP BY yourTable.Id
Based on your comment your query would be:
SELECT ID
,Field1
,Sum([Field1]) AS Expr1
From tblTest
GROUP BY ID, Field1;

Condition as a column named using AS "name" in mysql

I am trying to count line that has columns which been repeated (their value) more than x times in mysql, every time I try to execute this query I get an error :
SELECT DISTINCT
idLogin, count(idLogin ) AS "cou"
FROM
`products` AS t
GROUP BY
idLogin
HAVING
t.cou > 2
why this error is happening
Use this one
SELECT DISTINCT idLogin, count(idLogin ) AS cou FROM `products`
GROUP BY idLogin HAVING cou > 2
you can put that expression count(idLogin ) directly in having clouse....
it will not give any error.. and will be more understable as well....
or else you can do one thing -
select idLogin,cou from (
SELECT DISTINCT idLogin, count(idLogin ) AS cou
FROM products
GROUP BY idLogin ) t
where t.cou >2
Remove the double quotes from the aliased column name.
MySQL uses single back-quotes for escaping table and column names, not double quotes.
The correlation name t does not have a column cou. Just use this:
HAVING cou > 2
PS: DISTINCT is redundant in your query. The GROUP BY ensures there will only be one row per distinct value of idLogin.