首先:我不太清楚在问题标题中放什么,我不知道如何调用这样的查询,也许这就是为什么我找不到任何答案。
我有一张无线电台表和一张溪流表。每个无线电台可以有多个流,用于不同的格式,比特率等。 我希望获得所有工作站的列表,并为给定的应用程序提供首选格式的流。
现在这就变得棘手了,我希望首选格式成为列表,我的数据库应该返回第一个合适的流。
所以我可能会有这样一个列表:('MP3','AAC','OGG')
然后我希望MySQL为每个站点返回“MP3”类型的流,但是如果它不存在则应返回该站的“AAC”流等等。 如果找不到合适的流,则不应该返回该站。
示例:
CREATE TABLE `stations` (
`id` INT(11),
PRIMARY KEY (`id`)
) ENGINE=InnoDB;
CREATE TABLE `streams` (
`id` INT(11),
`station` INT(11),
`media_type` ENUM('MP3', 'OGG', 'AAC', 'Flash'),
PRIMARY KEY (`id`),
KEY (`station`),
CONSTRAINT `fk_1` FOREIGN KEY (`station`) REFERENCES `stations` (`id`) ON DELETE CASCADE ON UPDATE CASCADE
) ENGINE=InnoDB;
INSERT INTO `stations` (`id`) VALUES (1), (2), (3);
INSERT INTO `streams` (`id`, `station`, `media_type`) VALUES (1, 1, 'MP3'), (2, 1, 'AAC'), (3, 2, 'Flash'), (4, 2, 'AAC'), (5, 3, 'Flash');
如果首选媒体类型列表为('MP3', 'AAC')
,则使用上述示例数据的所需结果应为:
station stream type
1 1 MP3
2 4 AAC
我试过了:
SELECT
st.id AS station_id,
str.id AS stream_id,
str.media_type,
FIELD(str.media_type, 'MP3', 'AAC') AS preference
FROM
stations st
LEFT JOIN
streams str ON str.station = st.id
GROUP BY
st.id
HAVING
MIN(preference)
但是,只返回1或0条记录,这取决于流表中的第一条记录是首选媒体类型,我不明白为什么。
我能找到的唯一解决方案是使用子查询对流进行排序,然后按station_id进行分组,如下所示:
SELECT sub.* FROM
(SELECT
st.id AS station_id,
str.id AS stream_id,
str.media_type
FROM
stations st
LEFT JOIN
streams str ON str.station = st.id
WHERE
str.media_type IN ('MP3', 'AAC')
ORDER BY
FIELD(str.media_type, 'MP3', 'AAC')
) AS sub
GROUP BY sub.station_id
但是这会导致子查询创建的临时表的全表扫描,性能是不可接受的。由于我们不能限制内部查询(因为它尚未分组),临时表将变得非常大。
B.T.W。,我正在运行MySQL 5.6
那么,我应该使用哪种查询来处理首选属性列表?
答案 0 :(得分:5)
如果您只想返回A1="XYZ"
B1="100000"
C1="52.00"
D1="office supplies"
A2="YZA"
B2="150000"
C2="-52.00"
D2="office supplies"
或'MP3'
存在的行,则不需要外部联接。
这是一个标准SQL解决方案,它将在mysql中按原样运行,请参阅fiddle:
'AAC'
添加更多媒体类型很容易,主要是剪辑和播放糊。 COALESCE根据CASE的顺序返回第一个匹配的媒体类型。
答案 1 :(得分:0)
修改强>
要获得每个无线电台的最高优先级流,您可以使用变量根据其media_type
值为每个无线电台对每个流进行排名,并仅选择排名为1的行:
select * from (
select *,
@rn := if(@prevStationId = station_id, @rn+1, 1) rn,
@prevStationId := station_id
from streams
where media_type in ('MP3','AAC')
order by station_id, FIELD(media_type,'MP3','AAC')
) t1 where rn = 1