-1

私は次の表を持っています:

ID   ActualDt   DueDt     Flag
--   -------    -------   ----    
1    01/03/12   09/13/12   Y
2    NULL       07/12/12   Y 
3    NULL       09/12/12   N
4    02/03/12   01/13/12   N

次の条件では、フラグをYとしてマークする必要があります。

1)ActualDtがnullでなく、DueDtがnullでなく、DueDt>ActualDtの場合

2)ActualDtがnullで、現在の日付に基づいてDueDtが期限を過ぎている場合

それ以外の場合、フラグ= N

ActualDtは文字列であることに注意してください

これをt-sqlでどのようにプログラムしますか

ケースステートメントが必要なことはわかっています。

4

3 に答える 3

2

私があなたの論理を正しく理解しているなら、それは次のようになるはずです:

SELECT
ID,
ActualDt,
DueDt,
CASE 
     WHEN ActualDt IS NOT NULL AND DueDt IS NOT NULL AND DueDt > ActualDt THEN 'Y'
     WHEN ActualDt IS NULL AND DueDt < getdate() THEN 'Y'
     ELSE 'N'
END as Flag
FROM YourTable

編集:アーロン(いつものように!)が指摘したように、私はあなたがあなたの日付に文字列を使用していることを見逃しました。あなたはActualDtを文字列として保存しているので、これはあなたに正しい結果を与えるつもりはありません

すべての日付値を日時にキャストできます...

SELECT
ID,
ActualDt,
DueDt,
CASE 
     WHEN cast(ActualDt as datetime) IS NOT NULL AND cast(DueDt as datetime) IS NOT NULL AND cast(DueDt as datetime) > cast(ActualDt as datetime) THEN 'Y'
     WHEN cast(ActualDt as datetime) IS NULL AND cast(DueDt as datetime) < getdate() THEN 'Y'
     ELSE 'N'
END as Flag
FROM YourTable

ただし、日付の形式とロケール設定(および日付形式の設定)によっては、SQLエラーまたは予期しない日付が発生する可能性があることに注意してください。

日付を日時として保存することをお勧めします-日付が文字列である理由を説明できますか?

于 2012-08-13T21:47:28.067 に答える
0

更新ステートメントが必要です。

update t
    set flag = (case when ActualDt is not null and DueDt is not null and
                          DueDt > cast(ActualDt as date)
                     then 'Y'
                     when ActualDt is null and DueDt is not null and
                          DueDt > cast(CURRENT_TIMESTAMP as date)
                     then 'Y'
                     else 'N'
                end)

このクエリは、日付の形式がデータベースのデフォルトの形式と一致することを前提としています。私のデータベースは米国標準に設定されているため、「01/03/12」は2012年1月3日と解釈されます。

于 2012-08-13T21:52:30.140 に答える
0

ここでの本当の解決策は、あなたの生活を楽にするために、日付を文字列として保存するのをやめることです。最初にこのテーブルから始めたとしましょう。

CREATE TABLE dbo.Nathan
(
 ID INT,   
 ActualDt VARCHAR(32),  
 DueDt VARCHAR(32),     
 Flag CHAR(1)
);
GO

INSERT dbo.Nathan VALUES
(1,'01/03/12','09/13/12','Y'),
(2, NULL     ,'07/12/12','Y'), 
(3, NULL     ,'09/12/12','N'),
(4,'02/03/12','01/13/12','N');

まず、文字列を完全に明確にします。

UPDATE dbo.Nathan
  SET ActualDt = CONVERT(CHAR(10), CONVERT(DATETIME, ActualDt, 1), 120),
      DueDt    = CONVERT(CHAR(10), CONVERT(DATETIME, DueDt   , 1), 120);

次に、データ型を修正しましょう。

ALTER TABLE dbo.Nathan ALTER COLUMN ActualDt DATE;
ALTER TABLE dbo.Nathan ALTER COLUMN DueDt DATE;
-- you should also update any parameters or code where
-- explicit types are used to populate these columns

これで、データは正しいデータ型を使用して保存され、比較は、このような面倒な文字列の解釈やデータ型の変換なしで機能します。要件は次のとおりです。

次の条件でフラグをYとしてマークする必要があり
ます。1)ActualDtがnullでなく、DueDtがnullでなく、DueDt> ActualDtの
場合2)ActualDtがnullで、現在の日付に基づいてDueDtが期限を過ぎている 場合それ以外の
場合、Flag = N

私にとってそれは次のように書かれています:

UPDATE dbo.Nathan
  SET Flag = CASE WHEN DueDt > ActualDt
    OR (ActualDt IS NULL AND DueDt < CURRENT_TIMESTAMP)
  THEN 'Y' ELSE 'N' END;

結果:

ID  ActualDt    DueDt       Flag
--  ----------  ----------  ----
1   2012-01-03  2012-09-13  Y  -- DueDt > ActualDt
2   NULL        2012-07-12  Y  -- past due
3   NULL        2012-09-12  N  -- not past due
4   2012-02-03  2012-01-13  N  -- DueDt NOT > ActualDt

これは、日付を文字列として保存し続けるよりもはるかに優れたアプローチだと思います。

于 2012-08-14T12:19:39.077 に答える