C# - 将时间值向下舍入到最接近的15分钟

12

有没有好的方法将介于0和59之间的数字四舍五入到最近的15。

我正在使用C# 3.5。

所以...

  • 1会变成0
  • 29会变成15
  • 30会变成30

等等等等。

非常感谢。

6个回答

29

x = x - (x % 15) 可以作为一种不依赖于整数除法的解决方案。


18

作为Datetime的扩展方法

public static DateTime RoundDown(this DateTime dateTime)
{
    return new DateTime(dateTime.Year, dateTime.Month, 
         dateTime.Day, dateTime.Hour, (dateTime.Minute / 15) * 15, 0);
}

使用

DateTime date = dateTime.Now.RoundDown();//for example

4
确保在其中某个地方使用抽象工厂模式以实现更松散的设计。 - Pierreten
4
嗨,我是一个扩展方法迷。我对此毫不道歉;p - johnc

5
乘以15,结果是多少?

你需要先确保x是整数类型,或者至少将x/15转换为整数类型。 - Reed Copsey

4
我不知道是否有类似于.Round(...)的库调用,也许扩展方法会更适合?
我会选择一个简单的IF语句。
如果速度是一个问题,尝试为每个值编写扩展的switch语句。如果这是一个问题,请使用单元测试来查看哪个更快。
为了完整起见...
//...
[TestMethod]
    public void round_down()
    {
        Assert.AreEqual(-5.RoundDown(), 0);
        Assert.AreEqual(0.RoundDown(), 0);
        Assert.AreEqual(1.RoundDown(), 0);
        Assert.AreEqual(20.RoundDown(), 15);
        Assert.AreEqual(42.RoundDown(), 30);
        Assert.AreEqual(48.RoundDown(), 45);
        Assert.AreEqual(59.RoundDown(), 45);
        Assert.AreEqual(90.RoundDown(), 45);
    }

//...

public static class Ext
{
    public static int RoundDown(this int val)
    {
        if (val < 0)
            return 0;
        if (val < 15)
            return 0;
        if (val < 30)
            return 15;
        if (val < 45)
            return 30;
        return 45;
    }
}

3
为了增加可测试性(同时避免在堆栈上分配整数的开销),他还可以使用一个模拟框架来模拟整数。 - Pierreten
嗯,不是因为别的,只是因为我假设这是在一个网站上,可能会有很多类似的事情发生。 - Paul Kohler
我的假设是0是下边界(59是上边界)。 - Paul Kohler

3
您可以使用整数除法 -
int number = 43;
int newNumber = number / 15;
int rounded = newNumber * 15;

0

这就是取模运算符非常方便的地方

number - (number % 15)

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接