Mysql 查找最小值并包含正确的列值
我试图获得每次旅行的最低价格,并知道哪些旅行细节对应于每次旅行的最低价格 为此,我尝试了子查询、连接等各种变体,但由于没有主键,我无法找到它 我试图实现的是以最低价格获得旅行,然后将最低价格旅行的详细信息包含在记录中Mysql 查找最小值并包含正确的列值,mysql,sql,group-by,min,Mysql,Sql,Group By,Min,我试图获得每次旅行的最低价格,并知道哪些旅行细节对应于每次旅行的最低价格 为此,我尝试了子查询、连接等各种变体,但由于没有主键,我无法找到它 我试图实现的是以最低价格获得旅行,然后将最低价格旅行的详细信息包含在记录中 SELECT travel_id, persons, days, MIN(`price`) AS `price` FROM travel_details WHERE 1 GROUP BY `travel_id` HAVING MIN(price); 我的表
SELECT travel_id, persons, days, MIN(`price`) AS `price`
FROM travel_details
WHERE 1
GROUP BY `travel_id`
HAVING MIN(price);
我的表格列的简单版本,列有:
旅行id
,人员
,天数
,价格
这些列一起构成主键
可以为不同的人、天数和价格预订旅行。对于相同的travel\u id
、persons
和days
组合,也可能存在多个价格选项
例如:
2人的旅行id为100,4人的旅行id为100
我想要实现的是回报:
100、250,然后使用正确的对应值:
100,2,4250
101,2,5185
现在,我的结果只是混合了所有其他数据。当我将这些列包括在group by中时,它不仅会在travel\u id
上分组,还会在persons
上分组。然后它将返回旅行id
和人员
的所有组合
你知道怎么做吗
Select a.travel_id, a.persons, a.days, a.price from travel_details a
JOIN (Select travel_id,MIN(Price) as p from travel_details group by travel_id) b
on b.travel_id=a.travel_id and b.p=a.price
上面的查询使用自联接。派生表b将包含差旅id和最低价格。您可以使用()中的执行此操作:
SELECT * FROM travel_details t
WHERE (t.travel_id,t.price) IN(SELECT s.travel_id,min(s.price)
FROM travel_details s
GROUP BY s.travel_id)
GROUP BY t.travel_id; // this last group-by is to filter doubles when there are multiple records per travel with the lowest price.
你好@PeterH,这对你有用吗?嗨,sagi,谢谢你的回复。查询在我的示例数据库上运行,只有20K条记录,持续了3分钟以上,所以我取消了它。它需要在1秒内运行。通过多个单一查询,我可以做到这一点。然而,我不能相信mysql中没有选项可以在表中选择每组价格最低的记录。还有其他想法吗?是的,在表中的travel\u id,price
上添加索引。使用20k条记录需要一秒钟@peterhI会同意您的观点,但所有列都是主键,因此mysql数据库已经对它们进行了完全索引。第二,这会解决下面的回答中指出的“未定义变量”的事实吗?如果有多个最低价格的选项,例如,3人200欧元,以及4人200欧元,则此查询还将返回每次旅行的多个记录。如何解决该问题,使其每次旅行只选择一条记录。或者根本不可能……你到底为什么要设计一个所有列都是主键的表呢?尝试添加一个索引作为(旅行id,价格)
-一个索引,而不是两个@PeterHMultiplePK的
很好,不是所有列,但作为PK的价格听起来并不正确。许多索引可能会影响性能,这取决于您对表执行的查询。试试我的想法,在两列上都添加一个索引,不管PK的
,然后告诉我它是否有用,我认为应该这样做@Peterhi“未定义的_变量”,感谢您的回复。这种解决方案我也有一个子查询。然而,这样做的结果是,它将导致每组产生多个结果。例如:差旅id=102,记录中1人=3人,记录中2人=4人,两者的定价均为200欧元。上述查询将返回此旅行的两条记录_id=102。无法将“persons”添加到join查询的select字符串中,因此也无法将“b.price=a.price和b.persons=a.persons”添加到主select查询中。在我看来,您接受了错误的答案。如果另一个答案不适用于您,那么这表明您的设计中存在缺陷,而不是解决方案中的缺陷。这可能是,但有了这样的注释,请定义设计中的缺陷是什么。包含4列的普通表,所有这些列都必须是唯一的,并定义为主键列。或者是一个普通表,它有5列,其中1个UID列作为主键列,4个普通列具有值。如此基本的表格设置如何成为设计缺陷。问题是如何以最低的价格获得每次旅行1个完整且正确的记录。如果每次旅行都有多个相同-最低-价格的选项,但只有3人而不是4人,那么如何获得每次旅行的1条记录。对于“记录”,在你发表评论之前,我补充了Sagi的答案。通过最后一次“分组”,问题就解决了。所以,也许你没有看到,检查下面的答案。我很清楚这个黑客行为,谢谢。问题是它可能返回不确定的结果。
SELECT * FROM travel_details t
WHERE (t.travel_id,t.price) IN(SELECT s.travel_id,min(s.price)
FROM travel_details s
GROUP BY s.travel_id)
GROUP BY t.travel_id; // this last group-by is to filter doubles when there are multiple records per travel with the lowest price.
SELECT travel_id, persons, days, price
FROM (
SELECT
ROW_NUMBER() OVER(PARTITION BY travel_id, persons, days ORDER BY price) AS RowNum,
travel_id, persons, days, price
FROM travel_details
) X
WHERE X.RowNum = 1