Calculate Win/Loss Streak Query - sql

I'm trying to find a way to calculate win/loss streak for a user. My table has a field defined as "W/L" and each win is entered as "W" and each loss is entered as "L" Here is what the current table looks like:
ID Result
1 L
2 W
3 W
4 W
Here is an example I found, seems pretty straight forward but I'm apparently missing an operator though. Not sure what I'm missing.
SELECT SUM(CASE WHEN Result = 'W' THEN 1 ELSE 0 END) as Wins,
SUM(CASE WHEN Result = 'L' THEN 1 ELSE 0 END) as Losses
FROM Table1
Is it best to create a query for this or more suited for a VBA type function?

You can use something like,
SELECT
Sum(IIF(Result = 'W', 1, 0)) As TotalWins,
Sum(IIF(Result = 'L', 1, 0)) As TotalLooses
FROM Table1;

Related

SQL or operator how to use with having

i have a table which i am joining with with operator. I can have 2 combinations id that table FDEL - 1 or 0 and FDVE 1 or 0, what i would like to do is to dispay if - item has fdve, or item has fdel (and count) but it doesnt work (i can see all fdve, or all fdel)
select
lpad(purchase_id,10,0) as purchase_id,
sum(has_label_fdel) as FDEL_count,
case when LABELS like '%FDVE%' then 1 else 0 end as HAS_LABEL_FDVE,
sum(has_label_fdve) as FDVE_count
from
"SRC_ORACLEIWP"."PURCHASE_ANALYSIS_RULES"
group by
lpad(purchase_id,10,0),has_label_fdve
having FDVE_count>0 -- FDEL_count>0
You want one resut row per product, so group by product only. Use SUMfor counting and MAX for the aggregated yes/no.
select
lpad(purchase_id,10,0) as padded_purchase_id,
max(has_label_fdve) as has_labels_fdve,
sum(has_label_fdve) as fdve_count,
max(has_label_fdel) as has_labels_fdel,
sum(has_label_fdel) as fdel_count
from src_oracleiwp.purchase_analysis_rules
group by padded_purchase_id
having has_labels_fdve = 1
or has_labels_fdel = 1
order by padded_purchase_id;
I've changed your alias names slightly, so they are digfferent from the columns you have (because such ambiguities can sometimes lead to problems).
The check on labels like '%FDVE%' is unnecessary, because you already have the has_label_fdve flag, which is always 0 or 1. Or so it seems. If the flags can be null, use COALESCE on them or do use LIKE expressions.
If you don't have has_label_fdve and has_label_fdel yet, use the labels column instead:
select
lpad(purchase_id,10,0) as padded_purchase_id,
max(case when labels like '%FDVE%' then 1 else 0 end) as has_labels_fdve,
sum(case when labels like '%FDVE%' then 1 else 0 end) as fdve_count,
max(case when labels like '%FDEL%' then 1 else 0 end) as has_labels_fdel,
sum(case when labels like '%FDEL%' then 1 else 0 end) as fdel_count
from src_oracleiwp.purchase_analysis_rules
group by padded_purchase_id
having has_labels_fdve = 1
or has_labels_fdel = 1
order by padded_purchase_id;

How to create an alias that counts Ws, Ls, and Ds to create a record

I have a table with sports results with a column labeled 'Result' where the values in that column are either W, L, or D. I would like to create an alias column that will quickly count the Ws, Ls, and Ds from the whole table in that columns and display it as 'Count W-Count L-Count D'.
I'm very new to SQL and I haven't figured this specific of a request out, nor can I find the correct search terms in Google to discover a video or forum result for the situation I am looking for.
If you want the values in separate columns, use conditional aggregation:
select sum(case when result = 'W' then 1 else 0 end) as w_cnt,
sum(case when result = 'L' then 1 else 0 end) as l_cnt,
sum(case when result = 'T' then 1 else 0 end) as t_cnt
from t;
Best option go for group by
Select result, count(*) from table
where column IN ('W' , 'L' , 'D' )
group by result

Display Default Value Decode Oracle SQL

I am attempting to set values to zero if a user does not exist in one of my tables. Currently, I am using decode to count the number of users that meet a certain criteria and then display the result.
SELECT T.D_CODE,
T.C_NO,
SUM(DECODE(t.Value, 'A', 1, 0)) AS FirstValue,
SUM(DECODE(t.Value, 'B', 1, 0)) AS SecondValue,
SUM(DECODE(t.Value, 'C', 1, 0)) AS ThirdValue,
SUM(DECODE(t.Value, 'F', 1, 0)) AS LastValue
FROM Table T,
Table OtherTable S
WHERE T.T_SSN = S.SSN(+)
AND T.D_CODE = 'INF'
GROUP BY t.D_CODE,
T.C_NO;
The issue is that I have a third table (TT) that has additional values in it. If TT has a value that is not present in Table T, then I need to display that record with 0's for all of the Decode values.
Required output would look something like:
D_CODE, C_NO, FirstValue, SecondValue, ThirdValue, LastValue
INF 600 2 0 0 0
INF 501 0 0 1 0
INF 400 0 0 0 0
Where INF 400 does not exist in Table t, only in Table TT
Any suggestions?
Your problem is that you are filtering the users by T.D_CODE = 'INF' which means that any user that does not met that criteria will not come at all in the results. So, for what I understood of your question you need this:
SELECT T.D_CODE,
T.C_NO,
SUM(CASE WHEN T.D_CODE = 'INF' AND t.Value = 'A' THEN 1 ELSE 0 END) AS FirstValue,
SUM(CASE WHEN T.D_CODE = 'INF' AND t.Value = 'B' THEN 1 ELSE 0 END) AS AS SecondValue,
SUM(CASE WHEN T.D_CODE = 'INF' AND t.Value = 'C' THEN 1 ELSE 0 END) AS AS ThirdValue,
SUM(CASE WHEN T.D_CODE = 'INF' AND t.Value = 'D' THEN 1 ELSE 0 END) AS AS LastValue
FROM Table T
LEFT JOIN Table OtherTable S
ON T.T_SSN = S.SSN
LEFT JOIN AnotherTable TT
ON T.T_SSN = TT.SSN
GROUP BY t.D_CODE,
T.C_NO;
Since you didn't provide any more details about your TT table I just guessed the relation between it and the T table.
Side note: Always use the SQL ANSI [LEFT ]JOINs style.
ALSO Note that for your current query and current fetched fields tables S and TT are totally irrelevant, unless you didn't explain it right.

Conditional SUM with SELECT statement

I like to sum values in a table based on a condition taken from the same table called. The structure of the table as per below. The table is called Data
Data
Type Value
1 5
1 10
1 15
1 25
1 15
1 20
1 5
2 10
3 5
If the Value of Type 2 is larger than the Value of Type 3 then I like to subtract the Value of Type 2 from the sum of all the Values in the table. I'm not sure how to write the IF statements using Values looked up in the table. I have tried below but it doesn't work.
SELECT SUM(Value)-IF(SELECT Value FROM Data WHERE Type=2>SELECT Value
FROM Data WHERE Type=3 THEN SELECT Value FROM Data
WHERE Type=2 ELSE SELECT Value FROM Data WHERE Type=3) FROM Data
or
SELECT SUM(d.Value)-IIF(a.type2>b.type3, a.type2, b.type3)
FROM Data d, (SELECT Value AS type2 FROM Data WHERE Type=2) a,
(SELECT Value AS type3 FROM Data WHERE Type=3) b
If I follow your logic correctly, then this would seem to do what you want:
select d.value - (case when d2.value > d3.value then d2.value else 0 end)
from data d cross join
(select value from data where type = 2) d2 cross join
(select value from data where type = 3) d3 ;
EDIT:
If you want just one number, then use conditional aggregation:
select sum(value) -
(case when sum(case when type = 2 then value else 0 end) >
sum(case when type = 3 then value else 0 end)
then sum(case when type = 2 then value else 0 end)
else 0
end)
from data;
Thanks for pointing me in the right direction. This is what I came up with in the end. It is a little bit different to the reply above since I'm using MS Access
SELECT SUM(Value)-IIf(SUM(IIf(Type=2, Value, 0)>SUM(IIf(Type=3, Value, 0), SUM(IIf(Type=2, Value, 0), SUM(IIf(Type=3, Value, 0) FROM Data
It is them same as the second suggestion above but adapted to MS Access SQL.

Count the "ratio?" for wins and losses

I've already got this to work but it's a really bad approach and i need some help with factorization of my query.
SELECT `GameDate`,
COUNT(CASE
WHEN `P1Outcome`= 'win' AND P2Param = 'a' THEN 1
END) AS a_win,
COUNT(CASE
WHEN `P1Outcome`= 'loss' AND P2Param = 'a' THEN 1
END) AS a_loss,
COUNT(CASE
WHEN `P1Outcome`= 'win' AND P2Param = 'b' THEN 1
END) AS b_win,
COUNT(CASE
WHEN `P1Outcome`= 'loss' AND P2Param = 'b' THEN 1
END) AS b_loss
FROM games
WHERE `P2Param` IN ( 'a', 'b', 'c' )
GROUP BY GameDate
This will get me an query that i can use in my php application but i would like to skip having to make the actual ratio calculation in php and fetch it directly with SQL.
So basically what i've been trying to do is something similar to this:
COUNT(CASE
WHEN `P1Outcome`= 'win' AND P2Param = 'a' THEN 1 Else -1
END) AS a_ratio,
But just as the beginer i'm, i can't figure it out how i can make this to work.
EDIT:
Sorry for not explaining my regards in more details, here is the thing. I'm creating an statistics component and i need to fetch the ratio for a period of time in order to display it as an graph. So the following things are required:
GameDate (1,2,3,4... days ago)
The ratio for the player based on to different params (maps in this case)
So in short this is what i got at the moment:
GameDate a_win a_loss b_win b_loss
2011/04/25 x x x x
2011/04/23 x x x x
....
So everything works out great, but i would like to have the actual ratio calculation made in SQL because at the moment i need to make it in php e.g $ratio = $q[a_win]-$q[a_loss] and due to the fact that I've a lot of different param my query is like double the size because i need to fetch both the win and loss instead of just the ratio like i want in the first place.
SELECT `GameDate`,
SUM(CASE `P2Param`
WHEN 'a' THEN CASE P1Outcome WHEN 'win' THEN 1 ELSE -1 END
ELSE 0
END) AS a_ratio,
SUM(CASE `P2Param`
WHEN 'b' THEN CASE P1Outcome WHEN 'win' THEN 1 ELSE -1 END
ELSE 0
END) AS b_ratio
FROM games
WHERE `P2Param` IN ( 'a', 'b', 'c' )
GROUP BY GameDate
What is very important COUNT just returns number of rows regardless of what you count unless you use COUNT(DISTINCT ...) which in turn returns count of distinct values. To sum up some values which you produce for every row use SUM(...). Make sure what happens in your DBMS when an expression in the SUM() function evaluates to NULL - some databases will just make the whole SUM return NULL.
To get ratio of any kind of data you can do:
select _date_, (SUM(case when _your_test_ then 1 else 0 end) / count(1)) as ratio
from _yout_table_
group by _date_
And if you just want to calculate a sum of some values:
select _date_, SUM(case when _your_test_ then 1 else 0 end) as number_of_something
from _yout_table_
group by _date_
What about:
SELECT COUNT(id), P1Outcome, P2Param
FROM games
GROUP BY P2Param, P1Outcome
It will returns you a resultset with 3 columns:
counted values for param and outcome
outcome
param
With that you can do more in my opinion.
SELECT GameDate, P2Param, SUM(CASE WHEN P1Outcome = 'win' THEN 1 ELSE -1 END) AS ratio
FROM games
GROUP BY GameDate, P2Param