2014-09-25 73 views
0

我正在尝试编写查询以查找自行车叉上的英里数。此数字的计算方法是:将与叉上安装日期相关联的distance_reading(与Bicycle_Fork记录关联的Bicycle_Fork.start_date之后或之后的最小值reading_date)与扣除叉后的扣除日期(最大值为reading_date或在Bicycle_Fork.end_date之前,或者如果为空,则读取与当前日期最接近的读数)。我已经设法将odometer_reading的范围限制在适当的范围内,但我无法弄清楚如何找到每个里程表的最小和最大日期,以表示何时安装了叉子。当我只需查看匹配start_dateend_date的记录时,很容易,但用户无需为每个零件更改的日期输入新的里程表读数。我一直在研究这个查询几个小时,而且我找不到一种方法来使用MIN(),它不仅仅是将所有结果中的最小日期排除在外。MySQL查找与另一个表中的记录相关的最小和最大日期

问题:我如何才能找到最低reading_date以及与每个odometer_id关联的最大reading_date同时保持我的WHERE子句创建的限制?

如果这是不可能的,我打算将从第一个查询检索到的值存储在PHP数组中,并从那里处理它,但我希望能够在MySQL中找到解决方案。

下面是一个SQL拨弄数据库架构和查询的当前状态:http://sqlfiddle.com/#!2/015642/1

SELECT OdometerReadings.distance_reading, OdometerReadings.reading_date, 
OdometerReadings.odometer_id, Bicycle_Fork.fork_id 
    FROM Bicycle_Fork 
    INNER JOIN (Bicycles, Odometers, OdometerReadings) 
    ON (Bicycles.bicycle_id = Bicycle_Fork.bicycle_id 
    AND Odometers.bicycle_id = Bicycles.bicycle_id AND OdometerReadings.odometer_id = Odometers.odometer_id) 
    WHERE (OdometerReadings.reading_date >= Bicycle_Fork.start_date) AND 
    ((Bicycle_Fork.end_date IS NOT NULL AND OdometerReadings.reading_date<= Bicycle_Fork.end_date) XOR (Bicycle_Fork.end_date IS NULL AND OdometerReadings.reading_date <= CURRENT_DATE())) 

这是没有考虑到数据库的可能性旧的查询缺少这一纪录

SELECT MaxReadingOdo.distance_reading, MinReadingOdo.distance_reading 
FROM 
(SELECT OdometerReadings.distance_reading, OdometerReadings.reading_date, 
OdometerReadings.odometer_id 
    FROM Bicycle_Fork 
    LEFT JOIN (Bicycles, Odometers, OdometerReadings) 
    ON (Bicycles.bicycle_id = Bicycle_Fork.bicycle_id 
    AND Odometers.bicycle_id = Bicycles.bicycle_id AND OdometerReadings.odometer_id = Odometers.odometer_id) 
    WHERE Bicycle_Fork.start_date = OdometerReadings.reading_date) AS MinReadingOdo 
INNER JOIN 
    (SELECT OdometerReadings.distance_reading, OdometerReadings.reading_date, 
    OdometerReadings.odometer_id 
    FROM Bicycle_Fork 
    LEFT JOIN (Bicycles, Odometers, OdometerReadings) 
    ON (Bicycles.bicycle_id = Bicycle_Fork.bicycle_id AND Odometers.bicycle_id 
    = Bicycles.bicycle_id AND OdometerReadings.odometer_id = Odometers.odometer_id) 
    WHERE Bicycle_Fork.end_date = OdometerReadings.reading_date) AS 
    MaxReadingOdo 
ON MinReadingOdo.odometer_id = MaxReadingOdo.odometer_id 

我试图让下面从SQL架构返回: 我最终将这些总结成一个号码,但我一直在与他们分开工作,以麦与起始日期或END_DATE对应e更容易检查值。

min_distance_reading | max_distance_reading | odometer_id 
============================================================= 
75.5     | 2580.5    | 1 
510.5     | 4078.5    | 2 
17.5     | 78.5     | 3 
+0

如果你喜欢,可以考虑以下这个简单的两步过程行动:1.如果您还没有这样做,请提供适当的DDL(和/或sqlfiddle),以便我们可以更轻松地复制问题。 2.如果您尚未这样做,请提供与步骤1中提供的信息相对应的所需结果集。 – Strawberry 2014-09-25 17:47:32

+0

感谢您的建议。我已经添加了一个SQL小提琴和一个理想的结果集。 – FlyingMolga 2014-09-25 18:13:18

回答

2

我不明白拼图的最后一部分,但这似乎接近...

SELECT MIN(ro.distance_reading) min_val 
    , MAX(ro.distance_reading) max_val 
    , ro.odometer_id 
    FROM OdometerReadings ro 
    JOIN odometers o 
    ON o.odometer_id = ro.odometer_id 
    JOIN Bicycle_Fork bf 
    ON bf.bicycle_id = o.bicycle_id 
    AND bf.start_date <= ro.reading_date 
GROUP 
    BY ro.odometer_id; 

http://sqlfiddle.com/#!2/015642/8

相关问题