英文:
JOIN tables, only selecting newest row from second table, and conditional on second table data
问题
对于第一个部分的问题,是的,你可以使用LEFT JOIN来获取每个人在Hair Colors表中的最新行。结果应该如下:
| People_index | Name | Color | Color-change time |
| ----- | ------ | ----- | ----- |
| 1 | Bob | Green | 5:45 |
| 2 | Susie | Black | 5:02 |
对于第二个部分的问题,你可以使用类似的SQL查询,但是在选择最新行的基础上,也只选择等于特定值的行。例如,只选择最新的头发颜色为绿色的人:
| People_index | Name | Color | Color-change time |
| ----- | ------ | ----- | ----- |
| 1 | Bob | Green | 5:45 |
英文:
Say I have two tables. One has the main details, such as each row is a person and has their name. The second row contains every revision when someone changes "Hair color".
People
People_index | Name |
---|---|
1 | Bob |
2 | Susie |
Hair colors
Hair_index | People_index | Color | Color-change time |
---|---|---|---|
1 | 1 | Brown | 5:03 |
2 | 1 | Red | 5:07 |
3 | 1 | Green | 5:45 |
4 | 2 | Black | 5:02 |
Is there a way to LEFT JOIN the two tables so that for each row in People, I only get the newest row for each person in Hair Colors?
So, the result should be:
People_index | Name | Color | Color-change time |
---|---|---|---|
1 | Bob | Green | 5:45 |
2 | Susie | Black | 5:02 |
And then, for the other part of my app, I'd like similar SQL, but on top of selecting the newest row, it also only selects the rows that equal a certain value. For example, only select people where the most recent hair color is Green:
People_index | Name | Color | Color-change time |
---|---|---|---|
1 | Bob | Green | 5:45 |
Right now, I just select all people first, then looping through the rows, I check whether the newest hair color row is Green for each person and decide whether to add the person to the final array that way, but it seems that it could be a lot more efficient.
答案1
得分: 1
尝试这个:
with PeopleAllHC as (
select
P.People_index
, P.Name
, HC.Color
, HC.Color_change_time
, Seq=row_number() over (partition by P.People_Index order by HC.Color_change_time desc)
from
People P
inner join
HairColors HC
on P.People_Index=HC.People_Index
)
select
People_index
, Name
, Color
, Color_change_time
from PeopleAllHC
where Seq=1
and Color='绿色'
我们在公共表达式(CTE)中获取所有的发色变化,使用row_number() over函数对它们按照变化时间从最近到最旧进行编号(这将分配1给最近的变化),将其称为PeopleAllHC。然后,我们选择Seq=1的行以限制输出为我们想要的颜色的最新变化。
(我已更改了您的表/列名称以避免使用分隔符 - 反引号/括号/双引号 - 这些取决于数据库管理系统;您可能需要相应调整它们。)
英文:
Try this:
with PeopleAllHC as (
select
P.People_index
, P.Name
, HC.Color
, HC.Color_change_time
, Seq=row_number() over (partition by P.People_Index order by HC.Color_change_time desc)
from
People P
inner join
HairColors HC
on P.People_Index=HC.People_Index
)
select
People_index
, Name
, Color
, Color_change_time
from PeopleAllHC
where Seq=1
and Color='Green'
We get all hair colour changes in the CTE, number the changes from most-recent to oldest using the row_number() over function (this will assign 1 to the most recent) calling it PeopleAllHC. We then select the rows with Seq=1 to limit the output to the latest with the color we want.
(I have changed your table/column names to avoid using delimiters -backticks/brackets/double quotes- ; these are dbms dependent; you may need to adjust them accordingly)
通过集体智慧和协作来改善编程学习和解决问题的方式。致力于成为全球开发者共同参与的知识库,让每个人都能够通过互相帮助和分享经验来进步。
评论