SQL查询调整

时间:2013-09-18 13:13:06

标签: sql sql-server-2008

最初的问题如下: SQL AdvancedQuery建议在进行此问题之前先查看初始问题,因为它包含相关信息。这个问题询问了以下内容并提供了以下信息;

  1. MMSI号码是代表船舶的唯一号码。一艘船 以唯一的消息类型发送不同的信息。我是 只对Message_ID 1和3感兴趣,因为他们有Latitudinal 和纵向信息。

    MMSI将在此数据库中重新进行复制(如上面的数据所示)(如果您想查看此数据,可通过链接找到该数据) 问题是,我需要有关船只的信息,遗憾的是只能在Message_ID 5中使用。例如Vessel_name和Ship_type。

  2. Ship_Type可能会改变!在这种情况下,它必须反映较晚的日期

  3. 我只需要属于以下纬度的船只 经度:纬度位置> 55和纬度< 85和经度> 50和经度< 141;

  4. ****这是已经改变的部分!我现在需要共享具有正确约束的MMSI的所有记录。例如以下记录:****

    MMSI     Message_ID    Time     Ship_Type  Vessel_Name   Latitude   Longitude
    
    2225555      1       2012-09-01     NULL      NULL       25.432345  145.123343
    
    上次忽略的

    现在将保留,因为MMSI号码2225555已经在指定的纬度和经度范围内有记录。

    以下查询适用于上一个问题中的所有规范:SQL AdvancedQuery

    ; WITH positions AS (
      SELECT MMSI
           , Message_ID
           , "Time"
           , Latitude
           , Longitude
      FROM   dbo.DecodedCSVMessages_Staging
      WHERE  Message_ID IN (1, 3)
      AND    Latitude  > 55
      AND    Latitude  < 85
      AND    Longitude > 50
      AND    Longitude < 141
    )
    , details AS (
      SELECT MMSI
           , Ship_Type
           , Vessel_Name
           , Row_Number() OVER (PARTITION BY MMSI ORDER BY "Time" DESC) As row_num
      FROM   dbo.DecodedCSVMessages_Staging
      WHERE  Message_ID = 5
    )
    SELECT positions.MMSI
         , positions.Message_ID
         , positions."Time"
         , details.Ship_Type
         , details.Vessel_Name
         , positions.Latitude
         , positions.Longitude
    FROM   positions
     INNER
      JOIN details
        ON details.MMSI    = positions.MMSI
       AND details.row_num = 1 -- Limit to "latest" ship details per MMSI
    

    我只是需要稍微调整一下。我不是程序员..因此,为我调整这种复杂性的查询现在不可能..谢谢..

2 个答案:

答案 0 :(得分:0)

您需要对同一个表进行另一次联接,以使用现有查询结果中的MMSI撤回所有记录。这样的事情应该这样做:

; WITH positions AS (
  SELECT MMSI
       , Message_ID
       , "Time"
       , Latitude
       , Longitude
  FROM   dbo.DecodedCSVMessages_Staging
  WHERE  Message_ID IN (1, 3)
  AND    Latitude  > 55
  AND    Latitude  < 85
  AND    Longitude > 50
  AND    Longitude < 141
)
, all_positions AS (
  SELECT MMSI
       , Message_ID
       , "Time"
       , Latitude
       , Longitude
  FROM   dbo.DecodedCSVMessages_Staging
  WHERE  Message_ID IN (1, 3)
)
, details AS (
  SELECT MMSI
       , Ship_Type
       , Vessel_Name
       , Row_Number() OVER (PARTITION BY MMSI ORDER BY "Time" DESC) As row_num
  FROM   dbo.DecodedCSVMessages_Staging
  WHERE  Message_ID = 5
)
SELECT all_positions.MMSI
     , all_positions.Message_ID
     , all_positions."Time"
     , details.Ship_Type
     , details.Vessel_Name
     , all_positions.Latitude
     , all_positions.Longitude
FROM   positions
 INNER
  JOIN details
    ON details.MMSI    = positions.MMSI
   AND details.row_num = 1 -- Limit to "latest" ship details per MMSI
 INNER
  JOIN all_positions 
    ON positions.MMSI    = all_positions.MMSI

编辑(在Clockwork-Muse的反馈之后):

当船舶在所需区域内多次报告时,您的原始查询将返回重复的行。要摆脱这种情况,只需在CTE位置使用DISTINCT:

; WITH positions AS (
  SELECT DISTINCT MMSI
       , Message_ID
       , "Time"
       , Latitude
       , Longitude
  FROM   dbo.DecodedCSVMessages_Staging
  WHERE  Message_ID IN (1, 3)
  AND    Latitude  > 55
  AND    Latitude  < 85
  AND    Longitude > 50
  AND    Longitude < 141
)
, all_positions AS (
  SELECT MMSI
       , Message_ID
       , "Time"
       , Latitude
       , Longitude
  FROM   dbo.DecodedCSVMessages_Staging
  WHERE  Message_ID IN (1, 3)
)
, details AS (
  SELECT MMSI
       , Ship_Type
       , Vessel_Name
       , Row_Number() OVER (PARTITION BY MMSI ORDER BY "Time" DESC) As row_num
  FROM   dbo.DecodedCSVMessages_Staging
  WHERE  Message_ID = 5
)
SELECT all_positions.MMSI
     , all_positions.Message_ID
     , all_positions."Time"
     , details.Ship_Type
     , details.Vessel_Name
     , all_positions.Latitude
     , all_positions.Longitude
FROM   positions
 INNER
  JOIN details
    ON details.MMSI    = positions.MMSI
   AND details.row_num = 1 -- Limit to "latest" ship details per MMSI
 INNER
  JOIN all_positions 
    ON positions.MMSI    = all_positions.MMSI

答案 1 :(得分:0)

; WITH valid_positions AS (
  SELECT MMSI
       , Message_ID
       , "Time"
       , Latitude
       , Longitude
  FROM   dbo.DecodedCSVMessages_Staging
  WHERE  Latitude  > 55
  AND    Latitude  < 85
  AND    Longitude > 50
  AND    Longitude < 141
)
, positions AS (
  SELECT MMSI
       , Message_ID
       , "Time"
       , Latitude
       , Longitude
  FROM   dbo.DecodedCSVMessages_Staging
  WHERE  Message_ID IN (1, 3)
  AND    EXISTS (
           SELECT *
           FROM   valid_positions
           WHERE  valid_positions.MMSI = DecodedCSVMessages_Staging.MMSI
         )
)
, details AS (
  SELECT MMSI
       , Ship_Type
       , Vessel_Name
       , Row_Number() OVER (PARTITION BY MMSI ORDER BY "Time" DESC) As row_num
  FROM   dbo.DecodedCSVMessages_Staging
  WHERE  Message_ID = 5
)
SELECT positions.MMSI
     , positions.Message_ID
     , positions."Time"
     , details.Ship_Type
     , details.Vessel_Name
     , positions.Latitude
     , positions.Longitude
FROM   positions
 INNER
  JOIN details
    ON details.MMSI    = positions.MMSI
   AND details.row_num = 1 -- Limit to "latest" ship details per MMSI

现在正在使用第三个CTE。

  1. valid_positions任何记录,其中坐标适合 您的标准,适用于任何Message_ID 2)
  2. positionsMessage_ID等于1或3 的所有记录 MMSI
  3. 中相应的valid_positions中有记录
  4. details:与以前相同。显示“最新”船舶/船只详情(Message_ID = 5)