MySQL Query for calculating weightage - mysql

To calculate the weightage of faults i've formulated this query,
Select id,faultdistribution, faulttype, faultseverity,
IF (faultdistribution='crs', COUNT(id) * 8, 0) +
IF (faultdistribution='configuration', COUNT(id) * 6, 0) +
IF (faulttype='bs' AND faultseverity='ft', COUNT(id) * 4, 0) +
IF (faulttype='bs' AND faultseverity='mj', COUNT(id) * 2, 0) +
IF (faulttype='bs' AND faultseverity='md', COUNT(id) * 5, 0) +
IF (faulttype='bs' AND faultseverity='mi', COUNT(id) * 3, 0) +
IF (faulttype='lf' AND faultseverity='ft', COUNT(id) * 2, 0) +
IF (faulttype='lf' AND faultseverity='mj', COUNT(id) * 1, 0)
FROM tbl_fault WHERE product='DAS' AND faultdistribution='missed'
What i intend to do is;
If Fault distribution= 'crs' then Fault * 8 + If Fault distribution= 'configuration' then Fault * 6 .........
As, there are records in database but i am not having any result from above query, help/suggestions required.
Regards

Becuase you are using Aggregate function COUNT in your query which returns only one row.But your query is running for all rows one by one which is wrong.
The COUNT() function returns the number of rows that matches a specified criteria.

Related

mysql how to show order number in result

so here is the query
select * from test order by pow(c1 - 8, 2) + pow(c2 - 5, 2) limit 3
is there any way to show order section -> "pow(c1 - 8, 2) + pow(c2 - 5, 2)" for each record in result ?
Just include it in the select:
select t.*, pow(c1 - 8, 2) + pow(c2 - 5, 2) as distance_squared
from test t
order by distance_squared
limit 3

How to auto increment a string with sql query

I am stuck at a point where i have to increment a string, and my strings are of type C001,SC001,B001
in my data base they are defined like
what i am trying to do do is write a query which check the previous highest code present into my db and the incriment it to +1
for example C001 -> C002,C009->C010,C099`->C100 and so on
Similarly for SC001->SC002,SC009->SC010,SC099->SC100 and so on
Similarly fro B001 -> B002,B009->B010,B099`->B100 and so on
I have a query which my friend has suggested me to use but that query only incriminating AAAA->AAAA01 , AAAA09->AAAA10
query is
SELECT id AS PrevID, CONCAT(
SUBSTRING(id, 1, 4),
IF(CAST(SUBSTRING(id, 5) AS UNSIGNED) <= 9, '0', ''),
CAST(SUBSTRING(id, 5) AS UNSIGNED) + 1
) AS NextID
FROM (
-- since you allow strings such as AAAA20 and AAAA100 you can no longer use MAX
SELECT id
FROM t
ORDER BY SUBSTRING(id, 1, 4) DESC, CAST(SUBSTRING(id, 5) AS UNSIGNED) DESC
LIMIT 1
) x
when i am replacing ID with CategoryCode it is giving me PrevID-C004 NextID-C00401 which is not my requirement i want PrevID-C004 and NextID->C005
NOTE i am using my sqlServer 5.1
Just try this one ,
SELECT
CategoryCode,CAST(CONCAT(LPAD(CategoryCode,1,0),LPAD(MAX(RIGHT(CategoryCode,
3)) + 1, 3, 0) ) AS CHAR),
FROM test
SELECT
SubCategoryCode,CAST(CONCAT(LPAD(SubCategoryCode,2,0),
LPAD(MAX(RIGHT(CategoryCode, 3)) + 1, 3, 0) ) AS CHAR),
FROM test
SELECT
BrandCode,CAST(CONCAT(LPAD(BrandCode,1,0), LPAD(MAX(RIGHT(BrandCode, 3)) +
1, 3, 0)) AS CHAR) FROM test

Does mysql query cache the dynamically calculated columns

I have a mysql query:
SELECT my_table.* WHERE SOUNDEX(my_col)='whatever' OR SUBSTR(SOUNDEX(my_col),4)='whatever' ORDER BY SUBSTR(SOUNDEX(my_col),4)='whatever',SOUNDEX(my_col)='whatever'
How many times will the substring function and soundex functions will actually be called? I mean for exactly same inputs will mysql cache the results over the span of one query?
If not, how can I make the change in the query so that each function is called minimum times possible.
MySQL would call this function four times for every returned row, to avoid this you can use a subquery, so instead of
SELECT *
FROM song
ORDER BY Substr(pre_calculated_soundex, 1, 1) =
Substr(Soundex("aaaa"), 1, 1)
+ Substr(pre_calculated_soundex
, 2, 1) =
Substr
(Soundex("aaaa"), 2, 1)
+ Substr(pre_calculated_soundex, 3, 1)
= Substr(Soundex("aaaa"), 3, 1)
+ Substr(pre_calculated_soundex, 4, 1
)
= Substr(Soundex("aaaa"), 4, 1)
You can do
SELECT * from (select *, Soundex("aaaa") as current_soundex from song)
ORDER BY
Substr(pre_calculated_soundex, 1, 1) = Substr(current_soundex , 1, 1)
+ Substr(pre_calculated_soundex, 2, 1) = Substr(current_soundex , 2, 1)
+ Substr(pre_calculated_soundex, 3, 1) = Substr(current_soundex , 3, 1)
+ Substr(pre_calculated_soundex, 4, 1) = Substr(current_soundex , 4, 1)

MySQL weighted average in a single query

I have a MySQL table which looks like this:
id load_transit load_standby hours_transit hours_standby
1 40 20 8 4
2 30 15 10 10
3 50 10 3 9
I need to do the following calculations:
(intermediate calculations)
hours_transit_total = 8+10+3 = 21
hours_standby_total = 4+10+9 = 23
(desired result)
load_transit_weighted_mean = 40*(8/21) + 30*(10/21) + 50*(3/21) = 36.667
load_standby_weighted_mean = 20*(4/23) + 15*(10/23) + 10*(9/23) = 13.913
Is it possible to do this in a single query? What would the best design be?
Note that
40*(8/21) + 30*(10/21) + 50*(3/21) =
(40*8)/21 + (30*10)/21 + (50*3)/21 =
(40*8 + 30*10 + 50*3)/21
and
20*(4/23) + 15*(10/23) + 10*(9/23) =
(20*4)/23 + (15*10)/23 + (10*9)/23 =
(20*4 + 15*10 + 10*9)/23
Which allows you to get the results you want using
SELECT sum(hours_transit * load_transit) / sum(hours_transit),
sum(hours_standby * load_standby) / sum(hours_standby)
FROM your_table
I just had this same question and built this little query I think makes it clear how to find the weighted average in a single query:
select sum(balance), sum(rate * balance / 5200) as weighted_rate, -- what I want
-- what you cannot do: sum(rate * balance / sum(balance))
sum(balance * rate) / sum(balance) as weighted_rate_legit -- ah thank you transitive math properties
from (
select '4600' as balance, '2.05' as rate from dual
union all
select '600' as balance, '2.30' as rate from dual
) an_alias;

Fastest way to calculate correlation in every row?

Well, I have a table data of millions of rows. I want to carry out correlation study for every row (from the 1st to the current row minus 1). For e.g. the 1st rows is omitted. The 2nd row's result column is to be supplied with the correlation using the 1st row. The 3rd row's result column is to be supplied with the correlation using the 1st and 2nd row. And so on.
Correlation for the entire table can be calculated using:
SELECT (Count(*)*Sum(x*y)-Sum(x)*Sum(y))/
(sqrt(Count(*)*Sum(x*x)-Sum(x)*Sum(x))*
sqrt(Count(*)*Sum(y*y)-Sum(y)*Sum(y))) AS TotalCorelation FROM Data;
I want to avoid using Joins as much as possible as it takes lots of time, sometimes even timeout error, above 300 seconds). What's the other alternative?
Example table Data Structure:
id, x, y, result
1 , 4, 2, null
2 , 6, 3, -0.2312
3 , 5, 5, 0.42312
4 , 6, 2, -0.5231
5 , 5, 5, 0.22312
6 , 3, 7, -0.2312
7 , 2, 9, 0.42231
8 , 7, 2, 0.32253
9 , 9, 5, 0.32431
id : primary key
x and y : The data
result: correlation
I think this is it:
SELECT d2.ID, d2.x, d2.y, d2.result,
(Count(*)*Sum(d1.x*d1.y)-Sum(d1.x)*Sum(d1.y))/
(sqrt(Count(*)*Sum(d1.x*d1.x)-Sum(d1.x)*Sum(d1.x))*
sqrt(Count(*)*Sum(d1.y*d1.y)-Sum(d1.y)*Sum(d1.y))) AS TotalCorelation
FROM Data d1
RIGHT JOIN Data d2 ON d1.id < d2.id
GROUP BY d2.ID
ORDER BY d2.ID
Without a closed form for calculating correlation of N+1 from N rows, you have to use a quadratic join like this.
I'm assuming that your basic formula is correct. But I'm not sure it is -- when I just run it on the total dataset, I don't get the result 0.32431, I get -0.552773693079.
Here's a linear implementation:
SET #SumX = 0;
SET #SumY = 0;
SET #Count = 0;
SET #SumX2 = 0;
SET #SumY2 = 0;
SET #SumXY = 0;
SELECT id, x, y,
#SumX := #SumX + x AS SumX,
#SumY := #SumY + y AS SumY,
#Count := #Count + 1 AS ct,
#SumX2 := #SumX2 + x*x AS SumX2,
#SumY2 := #SumY2 + y*y AS SumY2,
#SumXY := #SumXY + x*y AS SumXY,
IF(#Count > 1,
(#Count*#SumXY-#SumX*#SumY)/
(sqrt(#Count*#SumX2-#SumX*#SumX)*
sqrt(#Count*#SumY2-#SumY*#SumY)), NULL) AS TotalCorelation
FROM DATA
ORDER BY id
SQLFIDDLE