受信リクエストのタイムスタンプをデータベースに保存された値と比較しようとしています。SQL Server は当然、時間に関してミリ秒単位の精度を保持しており、.NET DateTime に読み込まれると、それらのミリ秒が含まれます。ただし、システムへの受信リクエストではその精度が提供されないため、ミリ秒を単純に削除する必要があります。
何か明らかなことを見逃しているような気がしますが、それを実行するエレガントな方法を見つけていません (C#)。
ベストアンサー1
以下は、ミリ秒の小数部を持つ DateTime に対して機能し、Kind プロパティ (Local、Utc、または Undefined) も保持します。
DateTime dateTime = ... anything ...
dateTime = new DateTime(
dateTime.Ticks - (dateTime.Ticks % TimeSpan.TicksPerSecond),
dateTime.Kind
);
または同等かつより短い:
dateTime = dateTime.AddTicks( - (dateTime.Ticks % TimeSpan.TicksPerSecond));
これは拡張メソッドとして一般化できます。
public static DateTime Truncate(this DateTime dateTime, TimeSpan timeSpan)
{
if (timeSpan == TimeSpan.Zero) return dateTime; // Or could throw an ArgumentException
// Some comments suggest removing the following line. I think the check
// for MaxValue makes sense - it's often used to represent an indefinite expiry date.
// (The check for DateTime.MinValue has no effect, because DateTime.MinValue % timeSpan
// is equal to DateTime.MinValue for any non-zero value of timeSpan. But I think
// leaving the check in place makes the intent clearer).
// YMMV and the fact that different people have different expectations is probably
// part of the reason such a method doesn't exist in the Framework.
if (dateTime == DateTime.MinValue || DateTime.MaxValue) return dateTime; // do not modify "guard" values
return dateTime.AddTicks(-(dateTime.Ticks % timeSpan.Ticks));
}
次のように使用されます。
dateTime = dateTime.Truncate(TimeSpan.FromMilliseconds(1)); // Truncate to whole ms
dateTime = dateTime.Truncate(TimeSpan.FromSeconds(1)); // Truncate to whole second
dateTime = dateTime.Truncate(TimeSpan.FromMinutes(1)); // Truncate to whole minute
...