【问题标题】:VS11 is steady_clock, steady?VS11是steady_clock,稳定吗?
【发布时间】:2012-07-14 08:13:10
【问题描述】:

我刚刚注意到<chrono.h> 中的以下代码,这对我来说没有意义。

struct system_clock
{
    static const bool is_monotonic = false; // retained
    static const bool is_steady = false;
};

class steady_clock
    : public system_clock
    {   // wraps monotonic clock
public:
    static const bool is_monotonic = true;  // retained
    static const bool is_steady = true;
    };

typedef steady_clock monotonic_clock;   // retained
typedef system_clock high_resolution_clock;

steady_clock 只是从不稳定的system_clock 派生而来,它怎么能稳定?

【问题讨论】:

    标签: c++ visual-c++ c++11 visual-studio-2012 chrono


    【解决方案1】:

    忽略您显示的代码(Jerry 的回答已经比我更好地解决了这个问题),大概 VC++ 2012 的 std::steady_clock稳定的,目前在 @987654321 上打开的多个错误报告证明了这一点@关于这个问题:

    【讨论】:

    • 仅供参考,这些链接已失效
    • @AndersK :此时 MS Connect long 消失了,因此希望链接标题能说明问题。
    【解决方案2】:

    暂时忽略 Microsoft 实现中的错误,从不稳定的时钟派生出稳定的时钟(或从非单调的时钟派生出单调的时钟)通常是非常有意义的。

    这是典型的“is-a”术语妨碍的地方之一,您需要真正考虑替代。特别是,情况并非“稳定的时钟不是不稳定的时钟,所以推导是错误的”。相反,情况是“在任何情况下都可以用稳定的时钟代替不稳定的时钟,因此推导很好”(同样适用于is_monotonic)。

    让我们考虑一个极端的例子——将原子钟直接连接到您的计算机。它是单调的,并且与您希望得到的一样稳定。假设它的输出频率(/分辨率)足够高,您可以使用它来代替您的系统可能可用的任何/所有其他时钟。

    【讨论】:

    • 对,这是接口继承,而不是实现继承(尽管通常在 C++ 中你可能两者都有)。稳定时钟满足不稳定时钟的接口。
    • @BenVoigt 我不认为“稳定的时钟满足不稳定时钟的接口”。 system_clock 支持from_time_tto_time_t,这对于steady_clock 来说意义不大。而steady_clockhigh_resolution_clock 可能不支持time_t 的全部范围(尤其是在32 位平台上)。
    • @YongweiWu:您将稳定与不稳定与相对时间与绝对时间混淆了。
    • @BenVoigt:steady_clock 不保证它是相对的还是绝对的。它可以是任何一个。你的观点是什么?
    • Ignoring bugs in Microsoft's implementation for the moment -- 说得好。这应该是默认状态。
    【解决方案3】:

    我实际上不同意“接受的答案”。这在微软方面是完全错误的,可能会导致不切实际的期望。 C++11标准要求system_clock实现to_time_tfrom_time_t,但是steady_clockhigh_resolution_clock没有这样的要求。这不是“is-a”关系,因为steady_clock 没有实现system_clock 的所有必需接口;也不应该。微软的行动对我来说没有意义:你怎么能指望steady_clockto_time_t 同时避免时间倾斜的问题?

    所以,简单地说,微软犯了一个错误,他们修复它的速度很慢。根据 Stephan T. Lavavej 的说法,他“没有时间在 2013 年的 RTM 中修复这个问题”,并且“所有的时钟都需要重新实现,正如几个活跃的错误所跟踪的那样”。见https://connect.microsoft.com/VisualStudio/feedback/details/719443/

    我猜一开始写垃圾假实现的不是他。

    编辑:我有点惊讶我被否决了,甚至有点沮丧。我的反对者和反对者,你是否意识到你正在合理化一个破碎的实施,可能很快就会改变和修复?请给我一个真正的实现,它具有 steady_clock 继承自 system_clock 并且没有损坏......

    2014 年 7 月的事实更新:从 Visual Studio 2014 CTP2 开始,steady_clock 不再继承自 system_clock....

    【讨论】:

    • 再次错过重点:虽然steady_clock 不需要to_time_t,但它当然是允许的。并且对于它如何获取to_time_teither 没有任何限制,因此从system_clock 继承也可以。
    • @MSalters。你错过了重点。尽管steady_clock 被允许实现to_time_t,但没有合适的语义。更重要的是,它可以使人们编写不可移植的代码,这些代码只能在MSVC中编译,而不能在其他平台上编译——例如,如果人们真的在接口需要system_clock&的地方使用steady_clock
    • 快速谷歌搜索也发现了这个链接:stackoverflow.com/questions/18361638/…。人们说了类似的话:“(to|from)_time_t 仅对系统时钟有意义。例如,high_resolution_clock 可能无法支持整个time_t 的范围。”
    • 再次查看 Jerry Coffin 的计算机示例,该计算机直接连接到 NIST 的一个原子钟。它将能够拥有一个稳定且绝对的steady_clock 实现,支持整个时间范围以及与time_t 之间的转换。 你的计算机的稳定时钟芯片不能做这些事情的事实并不排除这种可能性。
    • @BenVoigt:那么你可以说这个 atomic_clock 同时满足 system_clock 和 stable_clock。尽管如此,从接口的角度来看,steady_clock 不应该是 system_clock。对于 PC,这是一个有争议的问题,因为 system_clock 可以通过任何实际措施进行调整,而 stable_clock 则不应该。它们是不兼容的类型。一般来说,steady_clock 不能用 Liskov 替代 system_clock。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2011-03-07
    • 1970-01-01
    • 1970-01-01
    • 2011-11-08
    • 2010-10-11
    • 2016-05-23
    相关资源
    最近更新 更多