TimeSpan
SQL Server 2008 R2に.Netを保存しようとしています。
EFコードファーストはTime(7)
、SQL として保存する必要があることを示唆しているようです。
ただしTimeSpan
、.Netでは24時間よりも長い期間を処理できます。
TimeSpan
SQL Serverでの.Netの格納を処理する最良の方法は何ですか?
TimeSpan
SQL Server 2008 R2に.Netを保存しようとしています。
EFコードファーストはTime(7)
、SQL として保存する必要があることを示唆しているようです。
ただしTimeSpan
、.Netでは24時間よりも長い期間を処理できます。
TimeSpan
SQL Serverでの.Netの格納を処理する最良の方法は何ですか?
回答:
としてデータベースにBIGINT
保存し、ティックの数を保存します(例:TimeSpan.Ticksプロパティ)。
このようにして、取得時にTimeSpanオブジェクトを取得したい場合は、TimeSpan.FromTicks(value)を実行するだけで簡単にできます。
SELECT CAST(DATEADD(MILLISECOND, @Ticks/CAST(10000 AS BIGINT), '1900-01-01') AS TIME)
。'1900-01-01'
もちろん、日付は重要ではありません。これは、DATEADD(...)
関数が必要とする3番目の変数にすぎません。ティックには100ナノ秒があることを覚えておいてください。ただし、使用DATEADD(NANOSECOND...
するとオーバーフローが発生する可能性が高いため、ミリ秒を使用します。また、C#TimeSpan.TicksPerMillisecond
(10000である必要があります)を使用してこの事実を確認してください。
アドバイスありがとうございます。SQLサーバーには同等のものがないため。TimeSpanをティックに変換する2番目のフィールドを作成し、それをDBに保存しました。次に、TimeSpanの保存を禁止しました
public Int64 ValidityPeriodTicks { get; set; }
[NotMapped]
public TimeSpan ValidityPeriod
{
get { return TimeSpan.FromTicks(ValidityPeriodTicks); }
set { ValidityPeriodTicks = value.Ticks; }
}
あなたは24時間以上を保存する必要がない場合は、単に保存することができ、時間を SQL Serverの2008年以来、以降マッピングがあります
time (SQL Server) <-> TimeSpan(.NET)
24時間以内に保存するだけでよい場合は、変換は必要ありません。
ソース:http : //msdn.microsoft.com/en-us/library/cc716729(v=vs.110).aspx
ただし、24時間を超えて格納する場合は、ティックで格納し、データを取得して、TimeSpanに変換する必要があります。例えば
int timeData = yourContext.yourTable.FirstOrDefault();
TimeSpan ts = TimeSpan.FromMilliseconds(timeData);
Time
タイプは期間を表すものではなく、DateTime値のTime部分です。それはひどい選択ですTimeSpan
。
これは古い質問であることはわかっていますが、他のいくつかのオプションが記載されていることを確認したかったのです。
24時間を超えるTimeSpanをtime sqlデータ型フィールドに格納することはできないため。他にもいくつかのオプションがあります。
varchar(xx)を使用して、TimeSpanのToStringを格納します。この利点は、データ型や計算に精度をベイクする必要がないことです(秒対ミリ秒対日対2週間)。必要なのは、TimeSpan.Parse / TryParseを使用することだけです。これが私がすることです。
最初の日付+タイムスパンの結果を格納する2番目の日付、datetimeまたはdatetimeoffsetを使用します。データベースからの読み取りは、TimeSpan x = SecondDate-FirstDateの問題です。このオプションを使用すると、他の非.NETデータアクセスライブラリが同じデータにアクセスしても、TimeSpansを理解できなくなります。そのような環境がある場合に備えて。
タイムスパン(2倍または日時の差の計算)を生成する最も可能性の高いソースと一致するようにするには、.NET TimeSpan
をSQL Server DateTime
タイプとして保存します。
SQL Serverの、2の差があるためであるDateTime
「(S Cast
に対するFloat
S」と、次にCast
バックにDateTime
)単純にDateTime
1月1日、1900年例に対して。+0.1秒の差は1900年1月1日00:00:00.100であり、-0.1秒の差は1899年12月31日23:59:59.900です。
.NET TimeSpan
をSQL Server DateTime
タイプに変換するには、まず1900年1月1日の.NET DateTime
に追加して.NET タイプに変換しますDateTime
。もちろん、SQL Serverから.NETにそれを読み込むときは、最初にそれを.NETに読み込んでDateTime
から、1900年1月1日を引いて.NET に変換しますTimeSpan
。
期間がSQL ServerからDateTime
、およびSQL Server内で(つまりT-SQLを介して)生成され、SQL Serverが2016年より前のユースケースの場合、範囲と精度のニーズによっては、それらを保存するのは現実的ではない場合があります。 (ない言及ミリ秒などTicks
)ので、Int
タイプによって返されたDateDiff
(対BigInt
SS 2016 +さんからのDateDiff_Big
)ミリ秒〜67歳の〜24日分後にオーバーフローします。秒の。一方、このソリューションは、0.1秒までの精度で-147〜+8,099年の時間範囲を処理します。
警告:
これは、1900年1月1日との差がSQL ServerのDateTime
種類(1753年1月1日から9999年12月31日、別名-147から+8,099年)の範囲内の値になる場合にのみ機能します。.NET TimeSpan
側では、約29 k〜+29 k年間保持できるので、それほど心配する必要はありません。次の理由により、SQL ServerのDateTime2
種類(マイナス側の範囲はSQL Serverの範囲よりもはるかに大きいDateTime
)については触れませんでした。それはCast
、a)単純な方法では数値に変換できず、b)DateTime
の範囲で十分であるためです。ユースケースの大部分。
SQL ServerのDateTime
を経由して計算違いCast
に- -はFloat
-と-バック方法は0.1秒を超えて正確であるとは思われません。
データベースにタイムスパンを表示する方法はいくつかあります。
時間
このデータ型はSQL Server 2008以降でサポートされており、を格納するために推奨される方法TimeSpan
です。マッピングは必要ありません。また、SQLコードでもうまく機能します。
public TimeSpan ValidityPeriod { get; set; }
ただし、元の質問で述べたように、このデータ型は24時間に制限されています。
datetimeoffset
datetimeoffset
データ型は、に直接マップSystem.DateTimeOffset
。datetime
/ datetime2
からUTCへのオフセットを表すために使用されますが、に使用することもできますTimeSpan
。
ただし、データ型は非常に具体的なセマンティクスを示唆しているため、他のオプションも検討する必要があります。
datetime / datetime2
1つのアプローチは、datetime
またはdatetime2
タイプを使用することです。これは、データベースの値を直接処理する必要があるシナリオに最適です。ビュー、ストアドプロシージャ、またはレポート用。欠点はDateTime(1900,01,01,00,00,00)
、ビジネスロジックでタイムスパンを取得するために、日付から値を減算する必要があることです。
public DateTime ValidityPeriod { get; set; }
[NotMapped]
public TimeSpan ValidityPeriodTimeSpan
{
get { return ValidityPeriod - DateTime(1900,01,01,00,00,00); }
set { ValidityPeriod = DateTime(1900,01,01,00,00,00) + value; }
}
bigint
別のアプローチは、TimeSpanをティックに変換し、bigint
データ型を使用することです。ただし、このアプローチには、SQLクエリで使用するのが面倒であるという欠点があります。
public long ValidityPeriod { get; set; }
[NotMapped]
public TimeSpan ValidityPeriodTimeSpan
{
get { return TimeSpan.FromTicks(ValidityPeriod); }
set { ValidityPeriod = value.Ticks; }
}
varchar(N)
これは、人間が値を読み取れるようにする必要がある場合に最適です。CONVERT(datetime, ValidityPeriod)
関数を利用して、SQLクエリでこの形式を使用することもできます。必要な精度に応じて、8〜25文字が必要になります。
public string ValidityPeriod { get; set; }
[NotMapped]
public TimeSpan ValidityPeriodTimeSpan
{
get { return TimeSpan.Parse(ValidityPeriod); }
set { ValidityPeriod = value.ToString("HH:mm:ss"); }
}
ボーナス:期間と期間
文字列を使用して、NodaTimeデータ型、特にDuration
andを格納することもできますPeriod
。最初のものは基本的にTimeSpanと同じですが、後者はいくつかの日と月が他のものより長いか短いかを尊重します(つまり、1月は31日、2月は28または29です。夏時間のためにいくつかの日は長いまたは短いです。 )。このような場合、TimeSpanを使用するのは間違った選択です。
このコードを使用して、期間を変換できます。
using NodaTime;
using NodaTime.Serialization.JsonNet;
internal static class PeriodExtensions
{
public static Period ToPeriod(this string input)
{
var js = JsonSerializer.Create(new JsonSerializerSettings());
js.ConfigureForNodaTime(DateTimeZoneProviders.Tzdb);
var quoted = string.Concat(@"""", input, @"""");
return js.Deserialize<Period>(new JsonTextReader(new StringReader(quoted)));
}
}
そしてそれを次のように使います
public string ValidityPeriod { get; set; }
[NotMapped]
public Period ValidityPeriodPeriod
{
get => ValidityPeriod.ToPeriod();
set => ValidityPeriod = value.ToString();
}
私は本当に好きでNodaTime
、それはしばしば私をトリッキーなバグとたくさんの頭痛から救います。ここでの欠点は、SQLクエリで実際に使用できず、メモリ内で計算を行う必要があることです。
CLRユーザー定義型
また、カスタムデータ型を使用して、カスタムTimeSpan
クラスを直接サポートするオプションもあります。詳細については、CLRユーザー定義型を参照してください。
ここでの欠点は、データ型がSQLレポートで適切に動作しない可能性があることです。また、SQL Serverの一部のバージョン(Azure、Linux、Data Warehouse)はサポートされていません。
値の変換
EntityFramework Core 2.1以降、値の変換を使用するオプションがあります。
ただし、これを使用すると、EFは多くのクエリをSQL に変換できなくなり、クエリがメモリ内で実行されます。大量のデータをアプリケーションに転送する可能性があります。
したがって、少なくとも現時点では、それを使用せずに、クエリ結果をAutomapperでマップするだけの方がよいでしょう。
通常、以前に提案したように、TimeSpanは、TimeSpan.Ticksプロパティからの目盛りが入力されたbigintとして格納されます。TimeSpan.ToString()の出力が入力されたvarchar(26)としてTimeSpanを格納することもできます。私が書いた4つのスカラー関数(ConvertFromTimeSpanString、ConvertToTimeSpanString、DateAddTicks、DateDiffTicks)は、SQL側でTimeSpanを処理し、人為的に範囲を制限するハックを回避するのに役立ちます。間隔を.NET TimeSpanに保存できる場合は、これらの関数でも機能するはずです。さらに、これらの関数を使用すると、.NET Frameworkを含まないテクノロジを使用している場合でも、TimeSpansと100ナノ秒のティックを操作できます。
DROP FUNCTION [dbo].[DateDiffTicks]
GO
DROP FUNCTION [dbo].[DateAddTicks]
GO
DROP FUNCTION [dbo].[ConvertToTimeSpanString]
GO
DROP FUNCTION [dbo].[ConvertFromTimeSpanString]
GO
SET ANSI_NULLS OFF
GO
SET QUOTED_IDENTIFIER OFF
GO
-- =============================================
-- Author: James Coe
-- Create date: 2011-05-23
-- Description: Converts from a varchar(26) TimeSpan string to a bigint containing the number of 100 nanosecond ticks.
-- =============================================
/*
[-][d.]hh:mm:ss[.fffffff]
"-"
A minus sign, which indicates a negative time interval. No sign is included for a positive time span.
"d"
The number of days in the time interval. This element is omitted if the time interval is less than one day.
"hh"
The number of hours in the time interval, ranging from 0 to 23.
"mm"
The number of minutes in the time interval, ranging from 0 to 59.
"ss"
The number of seconds in the time interval, ranging from 0 to 59.
"fffffff"
Fractional seconds in the time interval. This element is omitted if the time interval does not include
fractional seconds. If present, fractional seconds are always expressed using seven decimal digits.
*/
CREATE FUNCTION [dbo].[ConvertFromTimeSpanString] (@timeSpan varchar(26))
RETURNS bigint
AS
BEGIN
DECLARE @hourStart int
DECLARE @minuteStart int
DECLARE @secondStart int
DECLARE @ticks bigint
DECLARE @hours bigint
DECLARE @minutes bigint
DECLARE @seconds DECIMAL(9, 7)
SET @hourStart = CHARINDEX('.', @timeSpan) + 1
SET @minuteStart = CHARINDEX(':', @timeSpan) + 1
SET @secondStart = CHARINDEX(':', @timespan, @minuteStart) + 1
SET @ticks = 0
IF (@hourStart > 1 AND @hourStart < @minuteStart)
BEGIN
SET @ticks = CONVERT(bigint, LEFT(@timespan, @hourstart - 2)) * 864000000000
END
ELSE
BEGIN
SET @hourStart = 1
END
SET @hours = CONVERT(bigint, SUBSTRING(@timespan, @hourStart, @minuteStart - @hourStart - 1))
SET @minutes = CONVERT(bigint, SUBSTRING(@timespan, @minuteStart, @secondStart - @minuteStart - 1))
SET @seconds = CONVERT(DECIMAL(9, 7), SUBSTRING(@timespan, @secondStart, LEN(@timeSpan) - @secondStart + 1))
IF (@ticks < 0)
BEGIN
SET @ticks = @ticks - @hours * 36000000000
END
ELSE
BEGIN
SET @ticks = @ticks + @hours * 36000000000
END
IF (@ticks < 0)
BEGIN
SET @ticks = @ticks - @minutes * 600000000
END
ELSE
BEGIN
SET @ticks = @ticks + @minutes * 600000000
END
IF (@ticks < 0)
BEGIN
SET @ticks = @ticks - @seconds * 10000000.0
END
ELSE
BEGIN
SET @ticks = @ticks + @seconds * 10000000.0
END
RETURN @ticks
END
GO
-- =============================================
-- Author: James Coe
-- Create date: 2011-05-23
-- Description: Converts from a bigint containing the number of 100 nanosecond ticks to a varchar(26) TimeSpan string.
-- =============================================
/*
[-][d.]hh:mm:ss[.fffffff]
"-"
A minus sign, which indicates a negative time interval. No sign is included for a positive time span.
"d"
The number of days in the time interval. This element is omitted if the time interval is less than one day.
"hh"
The number of hours in the time interval, ranging from 0 to 23.
"mm"
The number of minutes in the time interval, ranging from 0 to 59.
"ss"
The number of seconds in the time interval, ranging from 0 to 59.
"fffffff"
Fractional seconds in the time interval. This element is omitted if the time interval does not include
fractional seconds. If present, fractional seconds are always expressed using seven decimal digits.
*/
CREATE FUNCTION [dbo].[ConvertToTimeSpanString] (@ticks bigint)
RETURNS varchar(26)
AS
BEGIN
DECLARE @timeSpanString varchar(26)
IF (@ticks < 0)
BEGIN
SET @timeSpanString = '-'
END
ELSE
BEGIN
SET @timeSpanString = ''
END
-- Days
DECLARE @days bigint
SET @days = FLOOR(ABS(@ticks / 864000000000.0))
IF (@days > 0)
BEGIN
SET @timeSpanString = @timeSpanString + CONVERT(varchar(26), @days) + '.'
END
SET @ticks = ABS(@ticks % 864000000000)
-- Hours
SET @timeSpanString = @timeSpanString + RIGHT('0' + CONVERT(varchar(26), FLOOR(@ticks / 36000000000.0)), 2) + ':'
SET @ticks = @ticks % 36000000000
-- Minutes
SET @timeSpanString = @timeSpanString + RIGHT('0' + CONVERT(varchar(26), FLOOR(@ticks / 600000000.0)), 2) + ':'
SET @ticks = @ticks % 600000000
-- Seconds
SET @timeSpanString = @timeSpanString + RIGHT('0' + CONVERT(varchar(26), FLOOR(@ticks / 10000000.0)), 2)
SET @ticks = @ticks % 10000000
-- Fractional Seconds
IF (@ticks > 0)
BEGIN
SET @timeSpanString = @timeSpanString + '.' + LEFT(CONVERT(varchar(26), @ticks) + '0000000', 7)
END
RETURN @timeSpanString
END
GO
-- =============================================
-- Author: James Coe
-- Create date: 2011-05-23
-- Description: Adds the specified number of 100 nanosecond ticks to a date.
-- =============================================
CREATE FUNCTION [dbo].[DateAddTicks] (
@ticks bigint
, @starting_date datetimeoffset
)
RETURNS datetimeoffset
AS
BEGIN
DECLARE @dateTimeResult datetimeoffset
IF (@ticks < 0)
BEGIN
-- Hours
SET @dateTimeResult = DATEADD(HOUR, CEILING(@ticks / 36000000000.0), @starting_date)
SET @ticks = @ticks % 36000000000
-- Seconds
SET @dateTimeResult = DATEADD(SECOND, CEILING(@ticks / 10000000.0), @dateTimeResult)
SET @ticks = @ticks % 10000000
-- Nanoseconds
SET @dateTimeResult = DATEADD(NANOSECOND, @ticks * 100, @dateTimeResult)
END
ELSE
BEGIN
-- Hours
SET @dateTimeResult = DATEADD(HOUR, FLOOR(@ticks / 36000000000.0), @starting_date)
SET @ticks = @ticks % 36000000000
-- Seconds
SET @dateTimeResult = DATEADD(SECOND, FLOOR(@ticks / 10000000.0), @dateTimeResult)
SET @ticks = @ticks % 10000000
-- Nanoseconds
SET @dateTimeResult = DATEADD(NANOSECOND, @ticks * 100, @dateTimeResult)
END
RETURN @dateTimeResult
END
GO
-- =============================================
-- Author: James Coe
-- Create date: 2011-05-23
-- Description: Gets the difference between two dates in 100 nanosecond ticks.
-- =============================================
CREATE FUNCTION [dbo].[DateDiffTicks] (
@starting_date datetimeoffset
, @ending_date datetimeoffset
)
RETURNS bigint
AS
BEGIN
DECLARE @ticks bigint
DECLARE @days bigint
DECLARE @hours bigint
DECLARE @minutes bigint
DECLARE @seconds bigint
SET @hours = DATEDIFF(HOUR, @starting_date, @ending_date)
SET @starting_date = DATEADD(HOUR, @hours, @starting_date)
SET @ticks = @hours * 36000000000
SET @seconds = DATEDIFF(SECOND, @starting_date, @ending_date)
SET @starting_date = DATEADD(SECOND, @seconds, @starting_date)
SET @ticks = @ticks + @seconds * 10000000
SET @ticks = @ticks + CONVERT(bigint, DATEDIFF(NANOSECOND, @starting_date, @ending_date)) / 100
RETURN @ticks
END
GO
--- BEGIN Test Harness ---
SET NOCOUNT ON
DECLARE @dateTimeOffsetMinValue datetimeoffset
DECLARE @dateTimeOffsetMaxValue datetimeoffset
DECLARE @timeSpanMinValueString varchar(26)
DECLARE @timeSpanZeroString varchar(26)
DECLARE @timeSpanMaxValueString varchar(26)
DECLARE @timeSpanMinValueTicks bigint
DECLARE @timeSpanZeroTicks bigint
DECLARE @timeSpanMaxValueTicks bigint
DECLARE @dateTimeOffsetMinMaxDiffTicks bigint
DECLARE @dateTimeOffsetMaxMinDiffTicks bigint
SET @dateTimeOffsetMinValue = '0001-01-01T00:00:00.0000000+00:00'
SET @dateTimeOffsetMaxValue = '9999-12-31T23:59:59.9999999+00:00'
SET @timeSpanMinValueString = '-10675199.02:48:05.4775808'
SET @timeSpanZeroString = '00:00:00'
SET @timeSpanMaxValueString = '10675199.02:48:05.4775807'
SET @timeSpanMinValueTicks = -9223372036854775808
SET @timeSpanZeroTicks = 0
SET @timeSpanMaxValueTicks = 9223372036854775807
SET @dateTimeOffsetMinMaxDiffTicks = 3155378975999999999
SET @dateTimeOffsetMaxMinDiffTicks = -3155378975999999999
-- TimeSpan Conversion Tests
PRINT 'Testing TimeSpan conversions...'
DECLARE @convertToTimeSpanStringMinTicksResult varchar(26)
DECLARE @convertFromTimeSpanStringMinTimeSpanResult bigint
DECLARE @convertToTimeSpanStringZeroTicksResult varchar(26)
DECLARE @convertFromTimeSpanStringZeroTimeSpanResult bigint
DECLARE @convertToTimeSpanStringMaxTicksResult varchar(26)
DECLARE @convertFromTimeSpanStringMaxTimeSpanResult bigint
SET @convertToTimeSpanStringMinTicksResult = dbo.ConvertToTimeSpanString(@timeSpanMinValueTicks)
SET @convertFromTimeSpanStringMinTimeSpanResult = dbo.ConvertFromTimeSpanString(@timeSpanMinValueString)
SET @convertToTimeSpanStringZeroTicksResult = dbo.ConvertToTimeSpanString(@timeSpanZeroTicks)
SET @convertFromTimeSpanStringZeroTimeSpanResult = dbo.ConvertFromTimeSpanString(@timeSpanZeroString)
SET @convertToTimeSpanStringMaxTicksResult = dbo.ConvertToTimeSpanString(@timeSpanMaxValueTicks)
SET @convertFromTimeSpanStringMaxTimeSpanResult = dbo.ConvertFromTimeSpanString(@timeSpanMaxValueString)
-- Test Results
SELECT 'Convert to TimeSpan String from Ticks (Minimum)' AS Test
, CASE
WHEN @convertToTimeSpanStringMinTicksResult = @timeSpanMinValueString
THEN 'Pass'
ELSE 'Fail'
END AS [Test Status]
, @timeSpanMinValueTicks AS [Ticks]
, CONVERT(varchar(26), NULL) AS [TimeSpan String]
, CONVERT(varchar(26), @convertToTimeSpanStringMinTicksResult) AS [Actual Result]
, CONVERT(varchar(26), @timeSpanMinValueString) AS [Expected Result]
UNION ALL
SELECT 'Convert from TimeSpan String to Ticks (Minimum)' AS Test
, CASE
WHEN @convertFromTimeSpanStringMinTimeSpanResult = @timeSpanMinValueTicks
THEN 'Pass'
ELSE 'Fail'
END AS [Test Status]
, NULL AS [Ticks]
, @timeSpanMinValueString AS [TimeSpan String]
, CONVERT(varchar(26), @convertFromTimeSpanStringMinTimeSpanResult) AS [Actual Result]
, CONVERT(varchar(26), @timeSpanMinValueTicks) AS [Expected Result]
UNION ALL
SELECT 'Convert to TimeSpan String from Ticks (Zero)' AS Test
, CASE
WHEN @convertToTimeSpanStringZeroTicksResult = @timeSpanZeroString
THEN 'Pass'
ELSE 'Fail'
END AS [Test Status]
, @timeSpanZeroTicks AS [Ticks]
, CONVERT(varchar(26), NULL) AS [TimeSpan String]
, CONVERT(varchar(26), @convertToTimeSpanStringZeroTicksResult) AS [Actual Result]
, CONVERT(varchar(26), @timeSpanZeroString) AS [Expected Result]
UNION ALL
SELECT 'Convert from TimeSpan String to Ticks (Zero)' AS Test
, CASE
WHEN @convertFromTimeSpanStringZeroTimeSpanResult = @timeSpanZeroTicks
THEN 'Pass'
ELSE 'Fail'
END AS [Test Status]
, NULL AS [Ticks]
, @timeSpanZeroString AS [TimeSpan String]
, CONVERT(varchar(26), @convertFromTimeSpanStringZeroTimeSpanResult) AS [Actual Result]
, CONVERT(varchar(26), @timeSpanZeroTicks) AS [Expected Result]
UNION ALL
SELECT 'Convert to TimeSpan String from Ticks (Maximum)' AS Test
, CASE
WHEN @convertToTimeSpanStringMaxTicksResult = @timeSpanMaxValueString
THEN 'Pass'
ELSE 'Fail'
END AS [Test Status]
, @timeSpanMaxValueTicks AS [Ticks]
, CONVERT(varchar(26), NULL) AS [TimeSpan String]
, CONVERT(varchar(26), @convertToTimeSpanStringMaxTicksResult) AS [Actual Result]
, CONVERT(varchar(26), @timeSpanMaxValueString) AS [Expected Result]
UNION ALL
SELECT 'Convert from TimeSpan String to Ticks (Maximum)' AS Test
, CASE
WHEN @convertFromTimeSpanStringMaxTimeSpanResult = @timeSpanMaxValueTicks
THEN 'Pass'
ELSE 'Fail'
END AS [Test Status]
, NULL AS [Ticks]
, @timeSpanMaxValueString AS [TimeSpan String]
, CONVERT(varchar(26), @convertFromTimeSpanStringMaxTimeSpanResult) AS [Actual Result]
, CONVERT(varchar(26), @timeSpanMaxValueTicks) AS [Expected Result]
-- Ticks Date Add Test
PRINT 'Testing DateAddTicks...'
DECLARE @DateAddTicksPositiveTicksResult datetimeoffset
DECLARE @DateAddTicksZeroTicksResult datetimeoffset
DECLARE @DateAddTicksNegativeTicksResult datetimeoffset
SET @DateAddTicksPositiveTicksResult = dbo.DateAddTicks(@dateTimeOffsetMinMaxDiffTicks, @dateTimeOffsetMinValue)
SET @DateAddTicksZeroTicksResult = dbo.DateAddTicks(@timeSpanZeroTicks, @dateTimeOffsetMinValue)
SET @DateAddTicksNegativeTicksResult = dbo.DateAddTicks(@dateTimeOffsetMaxMinDiffTicks, @dateTimeOffsetMaxValue)
-- Test Results
SELECT 'Date Add with Ticks Test (Positive)' AS Test
, CASE
WHEN @DateAddTicksPositiveTicksResult = @dateTimeOffsetMaxValue
THEN 'Pass'
ELSE 'Fail'
END AS [Test Status]
, @dateTimeOffsetMinMaxDiffTicks AS [Ticks]
, @dateTimeOffsetMinValue AS [Starting Date]
, @DateAddTicksPositiveTicksResult AS [Actual Result]
, @dateTimeOffsetMaxValue AS [Expected Result]
UNION ALL
SELECT 'Date Add with Ticks Test (Zero)' AS Test
, CASE
WHEN @DateAddTicksZeroTicksResult = @dateTimeOffsetMinValue
THEN 'Pass'
ELSE 'Fail'
END AS [Test Status]
, @timeSpanZeroTicks AS [Ticks]
, @dateTimeOffsetMinValue AS [Starting Date]
, @DateAddTicksZeroTicksResult AS [Actual Result]
, @dateTimeOffsetMinValue AS [Expected Result]
UNION ALL
SELECT 'Date Add with Ticks Test (Negative)' AS Test
, CASE
WHEN @DateAddTicksNegativeTicksResult = @dateTimeOffsetMinValue
THEN 'Pass'
ELSE 'Fail'
END AS [Test Status]
, @dateTimeOffsetMaxMinDiffTicks AS [Ticks]
, @dateTimeOffsetMaxValue AS [Starting Date]
, @DateAddTicksNegativeTicksResult AS [Actual Result]
, @dateTimeOffsetMinValue AS [Expected Result]
-- Ticks Date Diff Test
PRINT 'Testing Date Diff Ticks...'
DECLARE @dateDiffTicksMinMaxResult bigint
DECLARE @dateDiffTicksMaxMinResult bigint
SET @dateDiffTicksMinMaxResult = dbo.DateDiffTicks(@dateTimeOffsetMinValue, @dateTimeOffsetMaxValue)
SET @dateDiffTicksMaxMinResult = dbo.DateDiffTicks(@dateTimeOffsetMaxValue, @dateTimeOffsetMinValue)
-- Test Results
SELECT 'Date Difference in Ticks Test (Min, Max)' AS Test
, CASE
WHEN @dateDiffTicksMinMaxResult = @dateTimeOffsetMinMaxDiffTicks
THEN 'Pass'
ELSE 'Fail'
END AS [Test Status]
, @dateTimeOffsetMinValue AS [Starting Date]
, @dateTimeOffsetMaxValue AS [Ending Date]
, @dateDiffTicksMinMaxResult AS [Actual Result]
, @dateTimeOffsetMinMaxDiffTicks AS [Expected Result]
UNION ALL
SELECT 'Date Difference in Ticks Test (Max, Min)' AS Test
, CASE
WHEN @dateDiffTicksMaxMinResult = @dateTimeOffsetMaxMinDiffTicks
THEN 'Pass'
ELSE 'Fail'
END AS [Test Status]
, @dateTimeOffsetMaxValue AS [Starting Date]
, @dateTimeOffsetMinValue AS [Ending Date]
, @dateDiffTicksMaxMinResult AS [Actual Result]
, @dateTimeOffsetMaxMinDiffTicks AS [Expected Result]
PRINT 'Tests Complete.'
GO
--- END Test Harness ---