Conditional selection of field values - sqlite

I am working on a database created for sport games.
I have one table called game:
-----------------------------
winner | team_id1 | team_id2
-----------------------------
I have a table teams
----------
id | title
----------
if winner = 1, team_id1 is the id of the winner team
if winner = 2, team_id2 is the id of the winner team
At the end I want for each games to get the title of the winner team followed by the title of the loser team.
It tried something like:
select tea1.title, tea2.title
from games gam
join teams tea1 on case
when gam.winner = 1 and gam.team1_id = tea1.id then 1
when gam.winner = 2 and gam.team2_id = tea1.id then 1
else 0
end = 1
join teams tea2 on case
when gam.winner = 2 and gam.team1_id = tea2.id then 1
when gam.winner = 1 and gam.team2_id = tea2.id then 1
else 0
end = 1
But the request hangs, I don't understand why.

Try to get winner or loser title in select clause instead of join conditions.
select
gam.winner,
case when gam.winner=1 then t1.title else t2.title end as winner_title,
case when gam.winner=2 then t1.title else t2.title end as loser_title
from
games gam
left join
teams t1
on
gam.team1_id = t1.id
left join
teams t2
on
gam.team2_id = t2.id

Related

Use case statement in where clause conditional to brings data according to user level

I am trying to create a query that brings me data according to user level and user id.
In my query, Level 1 is Administrator and can see everything, but other users can only see their records.
As i wrote this query works only for other users and not for Administrators.
If my LEVEL_TYPE = 1 then get all rows,
elsif my LEVEL_TYPE 1 then get all rows for this USER_ID.
SELECT cl.ID as ID,
cl.FIRST_NAME || ' ' || cl.LAST_NAME as PATIENT,
cl.AGE as AGE,
CASE
when cl.SEX ='M' then 'Άντρας' when cl.SEX ='F' then 'Γυναίκα'
when cl.SEX ='O' then 'Άλλο' when cl.SEX ='C' then 'Ζευγάρι' END as SEX,
sa.SESSION_AREA as SESSION_AREA,
ms.MARITAL_KIND as MARITAL_KIND,
wt.WORK_KIND as WORK_KIND,
ph.PATIENT_PHOTO as PATIENT_PHOTO,
case when cl.ACTIVE = 1 then 'ΕΝΕΡΓΟΣ'
when cl.ACTIVE = 2 then 'ΑΝΕΝΕΡΓΟΣ' end as PATIENT_ACTIVE,
pt.PAYMENT_KIND as PAYMENT_KIND
FROM CLIENTS cl
left join PAYMENT_TYPE pt on pt.ID = cl.PATIENT_TYPE
left join WORK_TYPE wt on wt.ID = cl.WORKING_CONDITION
left join MARITAL_STATUS ms on ms.ID = cl.MARITAL_STATUS
left join SESSIONS_AREA sa on sa.ID = cl.SESSION_AREA
left outer join PHOTOS ph on ph.CLIENTS_ID = cl.ID
inner join USER_PATIENTS up ON up.PATIENT_ID = cl.ID
inner join APP_USERS au on au.ID = up.USER_ID
WHERE (au.LEVEL_TYPE = 1) or
(au.LEVEL_TYPE <> 1 and up.USER_ID = (SELECT au.id
FROM APP_USERS au
WHERE au.APEX_ID = APEX_UTIL.GET_CURRENT_USER_ID))
ORDER BY cl.ACTIVE, cl.FIRST_NAME || ' ' || cl.LAST_NAME

How to UPDATE table a column according value from table b in SQLITE?

I have two tables. Table a and table b. They are connected with a.productID = b.productID. My question is How to update TABLE a.column IF TABLE b.culumn contain a specific value. I searched this problem but nothing helped me so I am asking you.
My code (it should be probably something like this):
SELECT Cars a
LEFT JOIN Season b ON a.productID = b.productID
SET a.type = "winter" CASE b.month < 3 OR b.month > 11
This does not work for me.
Just guessing what you want to do:
update Cars
set Cars.type = 'winter'
where exists (
select 1 from b where
b.productID = Cars.productID and (b.month < 3 OR b.month > 11)
)
Use an update with a correlated subquery:
UPDATE Cars a
SET a.type = 'winter'
WHERE
(SELECT b.month FROM Season b WHERE a.productID = b.productID) < 3 OR
(SELECT b.month FROM Season b WHERE a.productID = b.productID) > 11;

Sql Join between two tables using Entity framework - Trying to bind Gridview data from two tables

I have a gridview and originally I was binding data from one table (Table 1) and it was straightforward
gvUsers.dataSource = class.getUsers()
gvUsers.databind()
Function getUsers () As List (Of Users)
Return (From X in Table1 Select x).ToList()
End Function
However, some of my data are pointing to another table and there is no relationship between tables ( no foreign key)
Table 1
UID Name Age Blood Type Test Type
1 Sam 22 2 3
2 Jane 23 2 4
Table 2
ID Domain Code Description
1 Blood Type A A
2 Blood Type B B
3 Test Type 1 1
4 Test Type 2 2
Currently In the gridView I see Blood Type as values 2 and Test type 3, 4 ( The second table ID) but I should get the Code column values in Table 2.
How can I join those two tables - I know if there is foreign key but the fact a column name is equivelant to row data name makes it hard for me to figure out!
Cheers
Try Code
var result = (from p in Table1.AsEnumerable()
join Blood in Table2.AsEnumerable() on p.BloodType equals Blood .ID
join Test in Table2.AsEnumerable() on p.TestTyoe equals Test .ID
select new With
{
uid = p.UID,
Name = p.name,
Age = p.age,
BloodType = Blood.Code,
TestType = Test .Code
}).ToList();
Sql Query IS :
select UID ,Name,Age,B.Code as BloodType ,T.Code as TestType From Table1
inner join Table2 B on Table1.BloodType = B.ID
inner join Table2 T on Table1.TestType= T.ID
The Used Vb then
Dim result = from p in Table1.AsEnumerable()
join Blood in Table2.AsEnumerable() on p.BloodType equals Blood .ID
join Test in Table2.AsEnumerable() on p.TestTyoe equals Test .ID
select
p.UID,
p.name,
p.age,
Blood.Code,
Test.Code
gvUsers.DataSource = result
Try this one:
select table1.*, table2.* from table1
inner join table2 on table1.Blood Type = table2.id
You can select you desired columns from both tables.

Sum in Access Producing Total Sum and Placing This on Each Row

I am trying to create two columns: IntlAir and DomesticAir. I have a Boolean column in my data called International, and IntlAir returns Penalty + SellingFare when International is TRUE, and DomAir returns that sum when International = FALSE.
I would like to show this amount for each DK by Month.
My code is:
SELECT data.PostingMonth, data.DK_Number
, (SELECT sum(data.Penalty + data.SellingFare)
FROM data
WHERE data.International = TRUE) AS IntlAir
, (SELECT sum(data.Penalty + data.SellingFare)
FROM data
WHERE data.International = FALSE) AS DomesticAir
FROM data
GROUP BY data.PostingMonth, data.DK_Number
ORDER BY data.PostingMonth;
However, the output is giving me the total sum across all dks and across all months, and putting this value into every row.
Can someone tell me what I am doing wrong?
Perhaps this is all you need:
SELECT
PostingMonth,
DK_Number,
SUM((Penalty + SellingFare) * IIf(International, 1, 0)) AS IntlAir,
SUM((Penalty + SellingFare) * IIf(International, 0, 1)) AS DomAir
FROM [data]
GROUP BY PostingMonth, DK_Number
For the test data...
PostingMonth DK_Number International Penalty SellingFare
------------ --------- ------------- ------- -----------
1 1 False $10.00 $100.00
1 1 True $20.00 $200.00
2 1 False $30.00 $300.00
1 2 False $40.00 $400.00
1 2 False $50.00 $500.00
1 2 True $60.00 $600.00
...the above query returns
PostingMonth DK_Number IntlAir DomAir
------------ --------- ------- -------
1 1 $220.00 $110.00
1 2 $660.00 $990.00
2 1 $0.00 $330.00
There's a few ways to do that, though the one you chose wasn't one of them
Never sure where access is at in terms of sql but if you create a query that does this and call it queryAirTotal or somesuch
SELECT PostingMonth, DK_Number, International, sum(Penalty + SellingFare) as AirTotal
FROM data GROUP BY PostingMonth,DK_Number,International
That will give your totals by month, dk and type then you can do
Select t1.PostingMonth,t1.DK_Number,t1.AirTotal as IntlAir, t2.Total as DomesticAir
From queryAirTotal t1
Left Join queryAirTotal t2
On t1.PostingMonth = t2.PostingMonth and t1.DK_Number = t2.DK_Number
Where t1.International = TRUE and t2.International = FALSE
Though that will miss out Month/DKs where there was only Domestic air and no International air. You could sort that with a full outer join, which I believe access also struggles with.
You can get round that with a Union
Select t1.PostingMonth,t1.DK_Number,t1.AirTotal as IntlAir, t2.Total as DomesticAir
From queryAirTotal t1
Left Join queryAirTotal t2
On t1.PostingMonth = t2.PostingMonth and t1.DK_Number = t2.DK_Number
Where t1.International = TRUE and t2.International = FALSE
Union
Select t1.PostingMonth,t1.DK_Number,t1.AirTotal as IntlAir, t2.Total as DomesticAir
From queryAirTotal t1
Left Join queryAirTotal t2
On t2.PostingMonth = t1.PostingMonth and t2.DK_Number = t1.DK_Number
Where t1.International = TRUE and t2.International = FALSE

Retrieve a table to tallied numbers, best way

I have query that runs as part of a function which produces a one row table full of counts, and averages, and comma separated lists like this:
select
(select
count(*)
from vw_disp_details
where round = 2013
and rating = 1) applicants,
(select
count(*)
from vw_disp_details
where round = 2013
and rating = 1
and applied != 'yes') s_applicants,
(select
LISTAGG(discipline, ',')
WITHIN GROUP (ORDER BY discipline)
from (select discipline,
count(*) discipline_number
from vw_disp_details
where round = 2013
and rating = 1
group by discipline)) disciplines,
(select
LISTAGG(discipline_count, ',')
WITHIN GROUP (ORDER BY discipline)
from (select discipline,
count(*) discipline_count
from vw_disp_details
where round = 2013
and rating = 1
group by discipline)) disciplines_count,
(select
round(avg(util.getawardstocols(application_id,'1','AWARD_NAME')), 2)
from vw_disp_details
where round = 2013
and rating = 1) average_award_score,
(select
round(avg(age))
from vw_disp_details
where round = 2013
and rating = 1) average_age
from dual;
Except that instead of 6 main sub-queries there are 23.
This returns something like this (if it were a CSV):
applicants | s_applicants | disciplines | disciplines_count | average_award_score | average_age
107 | 67 | "speed,accuracy,strength" | 3 | 97 | 23
Now I am programmatically swapping out the "rating = 1" part of the where clauses for other expressions. They all work rather quickly except for the "rating = 1" one which takes about 90 seconds to run and that is because the rating column in the vw_disp_details view is itself compiled by a sub-query:
(SELECT score
FROM read r,
eval_criteria_lookup ecl
WHERE r.criteria_id = ecl.criteria_id
AND r.application_id = a.lgo_application_id
AND criteria_description = 'Overall Score'
AND type = 'ABC'
) reader_rank
So when the function runs this extra query seems to slow everything down dramatically.
My question is, is there a better (more efficient) way to run a query like this that is basically just a series of counts and averages, and how can I refactor to optimize the speed so that the rating = 1 query doesn't take 90 seconds to run.
You could choose to MATERIALIZE the vw_disp_details VIEW. That would pre-calculate the value of the rating column. There are various options for how up-to-date a materialized view is kept, you would probably want to use the ON COMMIT clause so that vw_disp_details is always correct.
Have a look at the official documentation and see if that would work for you.
http://docs.oracle.com/cd/B28359_01/server.111/b28286/statements_6002.htm
Do all most of your queries in only one. Instead of doing:
select
(select (count(*) from my_tab) as count_all,
(select avg(age) from my_tab) as avg_age,
(select avg(mypkg.get_award(application_id) from my_tab) as_avg-app_id
from dual;
Just do:
select count(*), avg(age),avg(mypkg.get_award(application_id)) from my_tab;
And then, maybe you can do some union all for the other results. But this step all by itself should help.
I was able to solve this issue by doing two things: creating a new view that displayed only the results I needed, which gave me marginal gains in speed, and in that view moving the where clause of the sub-query that caused the lag into the where clause of the view and tacking on the result of the sub-query as column in the view. This still returns the same results thanks to the fact that there are always going to be records in the table the sub-query accessed for each row of the view query.
SELECT
a.application_id,
util.getstatus (a.application_id) status,
(SELECT score
FROM applicant_read ar,
eval_criteria_lookup ecl
WHERE ar.criteria_id = ecl.criteria_id
AND ar.application_id = a.application_id
AND criteria_description = 'Overall Score' //THESE TWO FIELDS
AND type = 'ABC' //ARE CRITERIA_ID = 15
) score
as.test_total test_total
FROM application a,
applicant_scores as
WHERE a.application_id = as.application_id(+);
Became
SELECT
a.application_id,
util.getstatus (a.application_id) status,
ar.score,
as.test_total test_total
FROM application a,
applicant_scores as,
applicant_read ar
WHERE a.application_id = as.application_id(+)
AND ar.application_id = a.application_id(+)
AND ar.criteria_id = 15;

Resources