How to achieve below scenario with sql - mysql

The table structure
ID Name Cost
-------------------------
1 Peter 10
1 Peter 20
1 Peter 30
2 Lily 10
2 Lily 20
2 Lily 30
-------------------------
and I will like to achieve something as below for reporting
ID Name Cost
-------------------------
1 Peter 10
20
30
2 Lily 10
20
30
-------------------------
so what I have try is using left join but instead of giving me a results like above, it returns like this, exactly the same with the table structure.
ID Name Cost No Column Name
--------------------------------------
1 Peter 10
1 Peter 20
1 Peter 30
2 Lily 10
2 Lily 20
2 Lily 30
--------------------------------------

More of an expanded comment than an answer. Not properly tested or sure is the best method
select
case q.R when 1 then cast(q.id as nvarchar) else '' end as _id,
case q.r when 1 then q.nm else '' end as _nm,
q.cost
from
(
select
p.id,p.nm,p.cost,ROW_NUMBER() over (partition by p.id order by p.cost) as R
from tpeople as p
) as q
order by q.id

Related

MySQL Relative ranking of values in one column for all occurrences of a given key

I'm looking for some basic direction on how where to start looking to try and rank rows of a common key in a query.
Imagine I have a table like this:
user_id | account_id | score
1 A 10
1 B 20
2 C 10
2 D 20
2 E 30
What I'm hoping to do is add a rank column for relative to each user_id where the highest score gets the top rank:
user_id | account_id | score | rank
1 A 10 2
1 B 20 1
2 C 10 3
2 D 20 2
2 E 30 1
Just looking for some basic direction in terms of which way to head :/
You can use subquery
select
*,
(select count(1)+1 from your_table b where a.user_id=b.user_id and a.score<b.score) as rank
from your_table a
Output
1 A 10 2
1 B 20 1
2 C 10 3
2 D 20 2
2 E 30 1

How to check for one value in multiple rows

Whats the best way to check if different groups of rows in a table with the same GroupID such as different teams have a SINGLE captain? Captain Identifier for example could be '10', so its crucial that it goes through multiple records with the same groupID and checks to see if theres ONLY ONE record with the positionID as '10'. I need it to do it for all teams, i.e all groupID's
-------------------------------------------------
ID | Group ID | Name | Position|
-------------------------------------------------
1 1 John 3
2 1 jim 3
3 1 Hahn 4
4 1 Mary 4
5 1 Moe 4
6 1 Charlie 10
7 2 taylor 4
8 2 Geoff 4
9 2 adam 4
10 2 cam 10
11 3 sharon 2
12 3 tony 4
13 3 steve 3
14 3 eve 4
15 3 gwen 10
--------------------------------
So what I need it to do is check that every groupID only had ONE 10 as the position.
Thanks in advance guys. Check out the image link at the bottom.
im using mysql btw
Sorry if this is badly described
If I understood you - I think you need something like :
select groupId, sum(case when positionID='10' then 1 else 0 end) as captains
from tbl_name
group by groupID
having captains = 1
am I close???
If I understood you correctly, you want an indication that will tell you whether the groupID had more then one captain.
So what you need is this:
select groupID,case when cnt = 1 then 1 else 0 end as IND_ONE_CAPTAIN from (
select groupID, sum(case when positionid = '10' then 1 else 0 end) as cnt
from players
group by groupID)
Now IND_ONE_CAPTAIN columns consist 1 or 0, 1 is for the group id only had 1 captain, and 0 is when they had more.

Can I use one query to count two columns in SQL

I have
office
office_id name
--------- -----------------
1 office1
2 office2
3 office3
person
uid office_id age gender
---------------------------
1 1 20 male
2 1 20 female
3 1 20 male
4 1 21 male
5 2 20 male
6 3 20 male
Is it possible I can use ONE query to get
office_id name age_20 male
-----------------------------
1 office1 3 3
2 office2 1 1
3 office3 1 1
Yes, you can. MySQL support boolean arithmethic and I think this is the shortest way to do it. If you want a more RDBMS friendly, use CASE WHEN age = 20 THEN 1 ELSE 0 END.
SELECT a.office_ID,
a.name,
SUM(age = 20) age_20,
SUM(gender = 'Male') male
FROM office a
LEFT JOIN person b
ON a.Office_ID = b.office_ID
GROUP BY a.office_ID, a.name
SQLFiddle Demo

Select min/max from multiple items

I'll try to explain it as simple as possible:
First some database structure with dummy data.
Structure
tb_spec_fk
feature value
-----------------
1 1
1 2
1 3
1 4
1 5
2 2
2 3
3 1
3 4
4 2
4 3
4 4
5 1
5 3
5 5
6 3
6 5
tb_spec_feature
feature_id filter
------------------
1 2
2 2
3 2
4 2
5 1
6 0
tb_spec_value
value_id name
----------------
1 10
2 20
3 30
4 40
5 50
Now, what I want is the follow result
Result
feature_id min_value max_value
---------------------------------
1 10 50
2 20 30
3 10 40
4 20 40
But how?
Logic
Get from the tb_spec_feature where "filter" equals 2 the highest and lowest values which are present in the tb_spec_value table and connected together trough the tb_spec_fk table.
My attemps
A lot! But I'll spare you :)
SELECT
f.feature_id AS feature_id,
MAX(value.name) AS max_value,
MIN(value.name) AS min_value
FROM tb_spec_feature AS f
JOIN tb_spec_fk AS fk ON f.feature_id=fk.feature
JOIN tb_spec_value AS value ON fk.value=value.id
WHERE f.filter=2
GROUP BY f.feature_id
The two JOIN statements "link" the a feature to a value. GROUP BY groups all rows with the same feature id, and then you can take the min or max or any other aggregate function on those columns.
Demo
Here is how you can do it
select
tsf.feature_id,
tsvl.name as Min_Value,
tsvr.name as Max_Value
from tb_spec_feature as tsf
inner join (select feature , MIN(value) MinV,MAX(value)MaxV from tb_spec_fk group by feature order by feature)as tsfkl on tsfkl.feature = tsf.feature_id
left join tb_spec_value as tsvl on tsvl.value_id = tsfkl.MinV
left join tb_spec_value as tsvr on tsvr.value_id = tsfkl.MaxV
where tsf.filter = 2
group by tsf.feature_id
Output
feature_id | Min_Value | Max_Value
---------------------------------
1 | 10 | 50
2 | 20 | 30
3 | 10 | 40
4 | 20 | 40
Fiddle Demo

complex sql query in sql server 2008

I have 4 major tables in my database.
Season --> seasonID
Trials --> trialID
Competition --> CID,name
Camps --> campID,DivisionID(FK)
Divisions ---> DivisionID
Contestants --->ContestantID
Now a contestant belongs to / are members of a divisions.
Then a division belongs to a camp.
All this leads to my Performance table.
PERFORMANCE TABLE
SeasonID|TrialID|CampID|DivID|CompetionID|CtestantID|Score1 |Score2 |Total
1 1 1 1 1 1 20 20 40
1 1 1 1 2 1 20 15 30
1 2 1 1 1 2 10 5 15
1 2 1 1 2 2 5 5 10
1 2 1 1 1 1 10 30 40
1 2 1 1 2 1 20 10 30
How can I query this performance table to give me the competition name, total score and rank (ranking over total score) of each contestant in each competition by trials and by seasons?
Example:
In season 1 and trial 2 I want to have:
SeasonID| TrialID | ContestantID| Competition | TotalScore | Rank
1 2 1 1 40 1
1 2 2 1 15 2
1 2 1 2 30 1
1 2 2 2 10 2
How do I go about this? I have tried table variables, pivot and joins but I can only rank by competitions, but I don't how to aggregate the results to get the result above!
I'm not exactly sure how you calculated your desired results. I think this is what you are after but, if so, the TotalScore in the desired results of your question should be 10 for the last record, not 20.
SELECT SeasonID, TrialID, ContestantID, CompetitionID, Total,
DENSE_RANK() OVER(PARTITION BY CompetitionId ORDER BY Total DESC) AS [Rank]
FROM PerformanceTable