2016-06-20 15 views
0

私はdd.hh:mm:ss.nnnnn形式の値を持っています。いくつかの例は32.11:45:40.93877,11:45:30.32012であり、文字列形式です。dd.hhを追加:mm:ss.nnnnn SQL ServerのDatetimeに時刻形式

文字列形式のdatetime値以上の実行を追加したいと思います。値30.12:43:10.98222は、30日12時間43分10秒および98222ミリ秒として表すことができます。

は、私は、次のコード(機能)の結果を得るために書いた:

擬似コード:

split the string split(5.11:45:40.90399, ':') and add into #temptable(id, value). 

while(0 < @counter) 
    select @val = value from #tempTable where id = @counter 

    if (@counter = 0) 
     split '5.11' in 5 and 11 by using charindex, substring, left, Convert to Int function. Also handle availability of day value 
     datetimevalue = dateadd(day,5,datetimevalue) 
     datetimevalue = dateadd(hour, 11, datetimevalue) 

     if (@counter = 1) 
      datetimevalue = dateadd(minute, 45, datetimevalue) 
     if (@@counter = 2) 
      split 40.90399 into 40 and 90399 

     datetimevalue = dateadd(second, 40, datetimevalue) 
     datetimevalue = dateadd(millisecond, 90399, datetimevalue) 
End of while loop 

return datetimevalue 

我々は代替ソリューションまたは一部の変更は、上記のプロセスを簡素化することはできますか?

今のところ私はhh:mm:ssを秒に変換して秒として追加して、dateadd関数の呼び出しを減らすことを考えていました。

+0

はよくない日のthats。その時間です。例えば:5日11時間45分40秒。日時の値にtimespanを追加する方法がわからない –

+0

OK文字列をより詳しく見ることでそれを見たことがありますが、それはあなたの質問。 –

+0

これはまともな文字列スプリッタを持っていれば、それほど悪くはありません。私はこれを使用します。 http://www.sqlservercentral.com/articles/Tally+Table/72993/主な理由は、このスプリッタが超高速であるだけでなく、結果の行番号も返すためです。この場合、これは動作させる上で重要です。私はテーブル値関数は、これを扱うのが非常に簡単になると思います。ネストされたDATEADD呼び出しを使用して、単一のselect文でこれを行うことができるはずです。 –

答えて

1

まず、精度を得るためにDateTimeを使用できない場合は、DateTime2を使用する必要があります。

第2に、Mayur Patilが正当にコメントしたとおり、追加する値は日時の値ではなく時間の長さです。 Sqlサーバーには時間間隔データ型はありませんが、文字列値を文字列操作を使用して時間範囲に変換できます。

私は解決策を提案しました しかし、この解決策では解決できない問題があります:ミリ秒の部分が1000よりも大きくなる可能性があります(実際はそうです)。ちょっと離れてください。私はそれをナノ秒として扱うことを試みたが、それは私が期待していた結果を与えなかった。おそらく、他の誰かがそれを絞り込むか、またはそれを行うには良い方法を考え出すことがあります

まず、にすべてを追加するDateAdd関数を使用し、それがその後のコンポーネント、 だに時間を区切り、時間から日 次を分離します元の日付:

DECLARE @Date datetime2 = GETDATE() 

DECLARE @S as varchar(20) = '32.11:45:40.93877' 

;WITH CTE1 As 
(
    SELECT LEFT(@S, CHARINDEX('.', @S)-1) As TheDay, 
      REPLACE(SUBSTRING(@S, CHARINDEX('.', @S) + 1, LEN(@S) - CHARINDEX('.', @S)), ':', '.') As TheTime 
), CTE2 AS 
(
SELECT CAST(TheDay As int) As TheDays, 
     CAST(PARSENAME(TheTime, 4) As Int) As TheHours, 
     CAST(PARSENAME(TheTime, 3) As Int) As TheMinutes, 
     CAST(PARSENAME(TheTime, 2) As Int) As TheSeconds, 
     CAST(PARSENAME(TheTime, 1) As Int) As TheNanoSeconds 
FROM CTE1 
) 

SELECT @Date As OriginalDate, 
     @S As TimeSpan, 
     DATEADD(DAY, TheDays, 
      DATEADD(HOUR, TheHours, 
       DATEADD(MINUTE, TheMinutes, 
        DATEADD(SECOND, TheSeconds, 
         DATEADD(NANOSECOND, TheNanoSeconds, @Date) 
        ) 
       ) 
      ) 
     ) As Result 
FROM CTE2 

結果:

OriginalDate    TimeSpan    Result 
--------------------------- -------------------- --------------------------- 
2016-06-20 16:23:30.7470000 32.11:45:40.93877 2016-07-23 04:09:10.7470939 
関連する問題