[英]Have datetime.now return to the nearest second
我有一个“要求”为最近的秒提供时间戳......但不会比这更准确。 四舍五入或截断时间都可以。
我想出了这个可憎的东西
dateTime = DateTime.Parse(DateTime.UtcNow.ToString("U"));
(U 是长格式日期和时间。“2007 年 1 月 3 日 17:25:30”)
是否有一些不那么可怕的方法来实现这一目标?
编辑:所以从链接的截断毫秒答案(感谢约翰奥多姆)我打算这样做
private static DateTime GetCurrentDateTimeNoMilliseconds()
{
var currentTime = DateTime.UtcNow;
return new DateTime(currentTime.Ticks - (currentTime.Ticks % TimeSpan.TicksPerSecond), currentTime.Kind);
}
几乎没有那么可怕......但它确实保留了我关心的“那种”约会时间。 我的解决方案没有。
您可以将其实现为一个扩展方法,该方法允许您使用基础 Ticks 将给定的 DateTime 修剪到指定的精度:
public static DateTime Trim(this DateTime date, long ticks) {
return new DateTime(date.Ticks - (date.Ticks % ticks), date.Kind);
}
然后很容易将您的日期修剪为各种准确度,如下所示:
DateTime now = DateTime.Now;
DateTime nowTrimmedToSeconds = now.Trim(TimeSpan.TicksPerSecond);
DateTime nowTrimmedToMinutes = now.Trim(TimeSpan.TicksPerMinute);
您可以使用此构造函数:
public DateTime(
int year,
int month,
int day,
int hour,
int minute,
int second
)
所以它会是:
DateTime dt = DateTime.Now;
DateTime secondsDt = new DateTime(dt.Year, dt.Month, dt.Day, dt.Hour, dt.Minute, dt.Second);
如果你真的想把时间四舍五入到最接近的秒,你可以使用:
DateTime.MinValue
.AddSeconds(Math.Round((DateTime.Now - DateTime.MinValue).TotalSeconds));
但是,除非额外的半秒真的有所作为,否则您可以删除毫秒部分:
DateTime.Now.AddTicks( -1 * (DateTime.Now.Ticks % TimeSpan.TicksPerSecond));
尝试这个
TimeSpan span= dateTime.Subtract(new DateTime(1970,1,1,0,0,0, DateTimeKind.Utc));
return span.TotalSeconds;
使用选定的解决方案后,我很满意它运行良好。 但是,此处发布的扩展方法的实现不提供任何验证以确保您传入的刻度值是有效的刻度值。 它们也不保留被截断的 DateTime 对象的 DateTimeKind。 (当存储到像 MongoDB 这样的数据库时,这会产生微妙但相关的副作用。)
如果真正的目标是将 DateTime 截断为指定值(即小时/分钟/秒/毫秒),我建议改为在您的代码中实现此扩展方法。 它确保您只能截断到有效精度,并保留原始实例的重要 DateTimeKind 元数据:
public static DateTime Truncate(this DateTime dateTime, long ticks)
{
bool isValid = ticks == TimeSpan.TicksPerDay
|| ticks == TimeSpan.TicksPerHour
|| ticks == TimeSpan.TicksPerMinute
|| ticks == TimeSpan.TicksPerSecond
|| ticks == TimeSpan.TicksPerMillisecond;
// https://stackoverflow.com/questions/21704604/have-datetime-now-return-to-the-nearest-second
return isValid
? DateTime.SpecifyKind(
new DateTime(
dateTime.Ticks - (dateTime.Ticks % ticks)
),
dateTime.Kind
)
: throw new ArgumentException("Invalid ticks value given. Only TimeSpan tick values are allowed.");
}
然后你可以使用这样的方法:
DateTime dateTime = DateTime.UtcNow.Truncate(TimeSpan.TicksPerMillisecond);
dateTime.Kind => DateTimeKind.Utc
这是一种向上或向下舍入到最接近的秒而不只是修剪的舍入方法:
public static DateTime Round(this DateTime date, long ticks = TimeSpan.TicksPerSecond) {
if (ticks>1)
{
var frac = date.Ticks % ticks;
if (frac != 0)
{
// Rounding is needed..
if (frac*2 >= ticks)
{
// round up
return new DateTime(date.Ticks + ticks - frac);
}
else
{
// round down
return new DateTime(date.Ticks - frac);
}
}
}
return date;
}
它可以像这样使用:
DateTime now = DateTime.Now;
DateTime nowTrimmedToSeconds = now.Round(TimeSpan.TicksPerSecond);
DateTime nowTrimmedToMinutes = now.Round(TimeSpan.TicksPerMinute);
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.