“时间结束”是否有常数?


12

对于某些系统,时间值9999-12-31用作计算机可以计算的时间的“结束时间”。但是,如果改变了怎么办?将此时间定义为内置变量会更好吗?

在C和其他编程语言中,通常使用诸如MAX_INT或类似的变量来获取整数可能具有的最大值。为什么没有类似的函数MAX_TIME将变量设置为“时间结束”,对于许多系统而言,该时间通常为9999-12-31。为了避免硬编码到错误的年份(9999)的问题,这些系统是否可以为“时间结束”引入变量?

**真实示例**

End of validity date: 31/12/9999.(这样列出了正式文档)博客作者希望编写一个始终位于最上方的页面,即欢迎页面。因此,它有一个尽可能远的将来的日期:

3000?是的,您面临的欢迎页面发布于3000年1月1日。因此,该页面将永远保留在博客的顶部=)它实际上发布于2007年8月31日。


6
为什么?这似乎是可以通过实现正确的算法或数据结构来解决的问题。
欣快的2012年

16
我想大多数人都没有太多的担心Y10K问题尚未:-)特别是作为在此之前,我们也必然有一个Y2038问题,大概一对夫妇更...
彼得Török

2
@Thorbjörn,是的,那时大多数实时系统可能已经迁移。尽管如此,目前仍可能存在数量无法估量的旧嵌入式系统,旧数据库,过时文件格式的文件等。
PéterTörök2012年

14
我认为玛雅日历具有“时间结束”常数= 2012-12-21 ;-)
nikie 2012年

3
没有人知道“时间终结”的时间。
图兰斯·科尔多瓦

Answers:


47

问问自己为什么首先需要这样的变量。

最有可能的是,您在撒谎数据:每当需要“时间结束”变量时,您并不是在指实际的时间结束。而是您在表达诸如“该日期没有上限”,“此事件无限期继续”之类的内容。

因此,正确的解决方案是直接表达这些意图,而不是依赖魔术值:使用可为空的日期类型(其中null表示“未设置结束日期”),添加“不确定”布尔字段,使用多态包装( (可以是实际日期或特殊的“不确定”值),也可以是您的编程语言所提供的任何内容。

当然,正确的解决方案并不总是可行的,因此您最终可能最终会使用魔术值,但是当您这样做时,您必须根据具体情况决定一个合适的值,因为哪个日期可以,哪个日期不可以。有意义取决于所建模的域-如果要存储日志时间戳记,01/01/2999是一个合理的“时间终结”;我认为,从现在开始将近1000年后您的应用程序仍然可以使用的机会几乎为零。日历应用程序也有类似的考虑。但是,如果您的软件要处理科学数据,例如对地球气候的长期预测,该怎么办?那些人实际上可能希望展望未来一千年。或再向前走一步;天文学,这是一个非常正常的领域,可以在数十亿年的时间范围内进行非常大的推理,既通往未来,又走向未来。对于这些,01/01/2999是一个非常荒谬的任意最大值。OTOH是一种日历系统,能够处理未来10万亿年的时间,对于牙医预约跟踪系统来说,仅由于存储容量的原因,几乎是不切实际的。

换句话说,对于定义错误且任意定义的值,没有唯一的最佳选择。这就是为什么很少见到用任何一种编程语言定义的原因。那些通常不会将其命名为“时间结束”,而是将其命名为DATE_MAX(或Date.MAX),并将其表示为“可以存储在日期数据类型中的最大值”,而不是“时间结束”或“无限期”。


20
使用null表示特殊值实际上并没有比使用该特殊值好
Ryathal 2012年

2
@Ryathal好吧,我认为没有“核”错误,所以至少好一点……
K.Steff 2012年

8
@Ryathal:实际上不是。您可以对一个幻数执行很多操作,而对空值则不能执行。
Pieter B

21
@Ryathal- null在这种情况下,不是用作特殊值,而是用作的正确含义null,即“缺失”。因此,如果您的字段是ExpiryDate,则更正确:(null表示无有效期限)或END_OF_TIME(据我们所知不存在)。显然nullNoValue或类似的方法是更好的解决方案。
Scott Whitlock 2012年

3
@jwenting-他们没有区别,因为没有人。NULL表示它不存在,或者更人性化地讲,该值根本没有定义。
Ramhound 2012年

17

作为一个行业,我们一直在追求节省一些字节的过程中目光短浅和专断,例如

  • 99年12月31日
  • 2038年1月19日
  • T + 50年,希望我所参与的所有系统都已经过时或已被替换(或者我死了,以先到者为准)。

恕我直言,最好的选择是在“最大日期”上保持适当的主流抽象水平,并希望有一个通用的解决方案在时间到来之前解决该问题。

例如在.NET中,DateTime.MaxValue是任意的23:59:59.9999999, December 31, 9999, exactly one 100-nanosecond tick before 00:00:00, January 1, 10000。因此,如果我对自己的寿命的假设是错误的,并且在10000年到来,我宁愿希望使用更高版本的框架重新编译应用程序DateTime.MaxValue(例如,通过更改其基础类型)到新的任意值并将问题进一步拖延了数千年。

编辑

(加强tdammers的观点是,比伪造一个人工日期更有意义的是,向消费者明确强调我们没有结束日期这一事实。)

作为使用的替代方法null,其负面影响是与任何引用类型(包括.Net Nullable`)兼容,这可能会导致忘记使用FP语言进行检查的消费者产生NRE问题。Option或Maybe在可能返回或可能不返回的值周围键入包装。

伪代码:

Option<DateTime> LeaseExpiryDate(Home rental) 
{
    if (... expiry date can be determined ...)
       return Some(rental.ExpiryDate);
    else
       return None;
}

这样做的好处是,它迫使消费者对这两种情况进行推理。模式匹配在这里也很常见:

LeaseExpiryDate(myHome) match {
     case Some(expiryDate) => "Expired"
     case None => "No Expiry"
}

咄。我瞎了 没关系。
ott-- 2013年

也许有一天。我们将安排威廉·卡汉William Kahan)安排日期和时间。在我们必须之类的东西正,负无限时间戳“ NaT”价值观,等等
罗斯帕特森


7

您可能想要algebraic data typewith变体来表示无穷大date。然后定义比较,在该比较中,infinite变体将始终大于其他任何变体date

Scala中的示例:

sealed abstract class SmartTime extends Ordered[SmartTime] { x =>
        def compare(y: SmartTime) = {
                x match {
                        case InfiniteFuture => 1
                        case InfinitePast => -1
                        case ConcreteTime(x) =>
                                y match {
                                        case InfiniteFuture => -1
                                        case InfinitePast => 1
                                        case ConcreteTime(y) => x compare y
                                }
                }
        }
}
case class ConcreteTime(t: Long) extends SmartTime
case object InfiniteFuture extends SmartTime
case object InfinitePast extends SmartTime

http://ideone.com/K5Kuk


为后代引用答案中的代码。
致命的

2

将您的时间存储为64位IEE754双精度浮点数,您可以使用+INF。不要使用单精度,它只能精确到7位数字,这对于日期来说有点低。


1

Cocoa / Objective-C具有工厂方法[NSDate distantPast]和[NSDate distantFuture],它们完全代表您所指的事物。

当前实现返回的值是代表大约0 AD和4000 AD的常数,尽管不能保证或记录这些常数。


0

通常没有这样的值,因为它不能用作语言构造。

MAX_INT亲戚都是有目的的。它们可以在您的代码中用于检查溢出。如果您要创建和管理数组,向量等各种形式的大型数据对象,这将很有用。这也是一个特定于平台的价值。

MAX_DATE值的用例更难看。通常,这些只是值,它们不会用作程序结构的一部分,因此,循环使用的值不会对程序造成灾难性的后果(尽管可能会对数据造成不利影响)。而且,通常更严格地定义C,C ++等中的日期和时间类型;因此编写该程序的人不必担心它在平台之间可能会发生变化。


0

在我们执行的一个项目中,我们遇到了这样一种情况,即某些数据库的大小设置以一种使用软件30年后无法持续的方式进行。当客户当时问我们的首席工程师时:“那么,使用您的软件30年后,我们该怎么办?” 我们的首席工程师,像黄瓜一样凉爽,耸了耸肩回答:“我们去喝啤酒吧!”

关键是,仅使用将来足够的日期即可。届时您的软件可能会被升级或替换。:)

By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.