0

次のように定義された2つのテーブルがあります。

PTable:

[StartDate],    [EndDate],     [Type],     PValue
.................................................
2011-07-01      2011-07-07     001         5
2011-07-08      2011-07-14     001         10
2011-07-01      2011-07-07     002         15
2011-07-08      2011-07-14     002         20

TTable:

[Date],       [Type],     [TValue]
..................................
2011-07-01    001         11
2011-07-02    001         4
2011-07-03    001         0
2011-07-08    002         12
2011-07-09    002         12
2011-07-10    002         0

TTable の Tvalue 列を PTable の PValue で更新したいのですが、ここで TTable の [Date] は PTable の [StartDate] と [EndDate] の間にあり、DATEDIFF(DAY,TTable.[Date],PTable.[EndDate]) は最小です、および PTable.Type = TTable.Type

最終的な TTable は次のようになります。

[Date],       [Type],     [TValue]
..................................
2011-07-01    001         11
2011-07-02    001         4
2011-07-03    001         5       --updated
2011-07-08    002         12
2011-07-09    002         12
2011-07-10    002         20       --updated

私が試したのはこれです:

UPDATE [TTable] 
        SET 
        TValue = T1.PValue
        FROM TTable
        INNER JOIN PTable T1 ON 
            [Date] BETWEEN T1.StartDate AND T1.EndDate 
            AND DATEDIFF(DAY,[Date],T1.EndDate) = 
              (SELECT MIN( DATEDIFF(DAY,TTable.[Date],T.EndDate)  ) 
              FROM PTable T WHERE  TTable.[Date] BETWEEN T.StartDate AND T.EndDate
             )
            AND
            T1.[Type] = TTable.[Type]

このエラーが表示されます: 「外部参照を含む集約式で複数の列が指定されています。集約されている式に外部参照が含まれている場合、その外部参照は式で参照される唯一の列でなければなりません。」

後で編集:

TTable AS T と PTable AS P を考慮すると、更新の条件は次のとおりです。

1. T.Type = P.Type
2. T.Date BETWEEN P.StartDate AND P.EndDate
3. DATEDIFF(DAY,T.Date,P.EndDate) = minimum value of all DATEDIFFs WHERE P.Type = T.Type AND T.Date BETWEEN P.StartDate AND P.EndDate

後で編集 2: 申し訳ありませんが、PTable の最後の行を間違って入力したため (2011-07-14 ではなく 2011-08-10)、最終結果は間違っていました。

また、最初から試してみるべきだった、より簡単な方法で更新することもできました。

UPDATE TTABLE 
        SET 
        TValue = T1.PValue
        FROM TTable
        INNER JOIN PTABLE T1 ON 
            [Date] = (SELECT TOP(1) MAX(Date) FROM [TTABLE] WHERE [Date] BETWEEN T1.StartDate AND T1.EndDate)
            AND
            T1.Type = [TTABLE].Type

これにつきましては申し訳ございません。

4

1 に答える 1

0

それで、あなたは「DATEDIFF(DAY,TTable.[Date],PTable.[EndDate]) は最小です」と言って、私を混乱させました。タイプごとに毎週のエントリがある場合、特定の日付とタイプの組み合わせについては、1 つしか一致しないように思われます。これを試してみてください:

UPDATE TTABLE 
SET TValue = T1.PValue
FROM TTable
INNER JOIN PTABLE T1 ON T1.Type = [TTABLE].Type -- find row in PTable that the Date falls between
    and [Date] BETWEEN T1.StartDate AND T1.EndDate)
where 
    TValue = (  select MIN(TValue) -- finds the lowest TValue, 0 in example
                from TTable)) 

...更新しました...

そのため、最初に問題を間違って読んだようです。TValue が最も低い TTable エントリを更新すると思っていました。どうやってその印象を受けたのかわからない。それでも 0 かどうかを確認する必要があるようです。

UPDATE TTable 
SET TValue = T1.PValue
FROM TTable
INNER JOIN PTable T1 ON T1.Type = TTable.Type 
    and T1.EndDate = (
        SELECT top 1 EndDate 
        FROM PTable 
        WHERE Type=TTable.Type 
        ORDER BY abs(DATEDIFF(day,TTable.Date,PTable.EndDate)) desc)
WHERE 
    TValue = 0 -- only updating entries that aren't set, have a 0

これは、PTable に EndDate が 7/7 など、特定のタイプの行が 1 つある場合にのみ機能します。タイプ 001 の終了日が 7/7 のエントリが 2 つある場合は、2 つのエントリに結合されます。また、問題の日付から等距離にある 2 つのエントリがある場合、7/7 の EndDate と 7/13 の 1 つは両方とも 7/10 から 3 日です。EndDates がすべて 7 日間 (毎週) 離れている場合は問題ありません。

于 2014-08-04T13:04:40.560 に答える