【问题标题】:A strange error in chrono code "C2440: '<function-style-cast>' : cannot convert from '_CR' to 'std::chrono::milliseconds'"计时码中的一个奇怪错误“C2440: '<function-style-cast>' : cannot convert from '_CR' to 'std::chrono::milliseconds'”
【发布时间】:2012-09-01 22:15:17
【问题描述】:

我偶然发现了一个奇怪的错误

C2440: '' : 无法从 '_CR' 转换为 'std::chrono::milliseconds'

基本上相当于another question中的Howard Hinnant's代码。

这应该在 Visual Studio 2012 RC 上编译吗?这个问题的原因是什么?修复或解决方法怎么样?我的目标只是创建一个简单的计时器(没什么大不了的),因此,如果存在与此相关的内容,则会采取点 - 以及其他实现提示。

有问题的代码如下。 用法:

  timers::stopwatch w;
  w.start();
  std::cout << to_milliseconds(w.elapsed()) << std::endl;

头文件是(为简洁起见省略了实现)

namespace timers
{
    class stopwatch
    {
        public:
            typedef std::chrono::high_resolution_clock clock;
            typedef clock::time_point time_point;
            typedef clock::period period;
            typedef std::chrono::duration<float, period> duration;

            stopwatch();
            ~stopwatch();

            void start();
            void stop();
            void restart();
            void reset();

            duration elapsed() const;
       private:
            clock timer_;
            time_point start_point_;
            time_point end_point_;
            bool is_running_;

            void start_measuring();
            void stop_measuring();
     };
}

//Some convenience stuff...
namespace
{       
    long long to_milliseconds(timers::stopwatch::duration const& duration) { return   std::chrono::duration_cast<std::chrono::milliseconds>(duration).count(); }
    long long to_nanoseconds(timers::stopwatch::duration const& duration) { return std::chrono::duration_cast<std::chrono::nanoseconds>(duration).count(); }
    long long to_seconds(timers::stopwatch::duration const& duration) { return std::chrono::duration_cast<std::chrono::seconds>(duration).count(); }

}

编辑

根据 Howard Hinnant 的说明,在标头、实现文件和调用文件中有 #include &lt;chrono&gt;。错误指向 MS &lt;chrono&gt; 标头,错误在此代码中触发

// duration_cast
template<class _To,
    class _Rep,
    class _Period> inline
    typename enable_if<_Is_duration<_To>::value,
        _To>::type
        duration_cast(const duration<_Rep, _Period>& _Dur)
        {    // convert duration to another duration
            typedef typename ratio_divide<_Period, typename _To::period>::type _CF;
            typedef typename common_type<
            typename common_type<typename _To::rep, _Rep>::type,
                intmax_t>::type _CR;
                if (_CF::num == 1 && _CF::den == 1)
                    return (_To(static_cast<typename _To::rep>(_Dur.count())));
                else if (_CF::num != 1 && _CF::den == 1)
                    return (_To(static_cast<typename _To::rep>(static_cast<_CR>(_Dur.count())) * static_cast<_CR>(_CF::num)));
                else if (_CF::num == 1 && _CF::den != 1)
            return (_To(static_cast<typename _To::rep>(static_cast<_CR>(_Dur.count()) / static_cast<_CR>(_CF::den))));
                else
                    return (_To(static_cast<typename _To::rep>(xtatic_cast<_CR> _Dur.count()) * static_cast<_CR>(_CF::num) / static_cast<_CR>(_CF::den))));
}

特别是在&lt;chrono&gt; 的第 573 行,前面提到的是

 [...]
 else if (_CF::num != 1 && _CF::den == 1)
     return (_To(static_cast<typename _To::rep>(static_cast<_CR>(_Dur.count())) * static_cast<_CR>(_CF::num)));

如果它在我的代码中的某处或 VC++ &lt;chrono&gt; 标头中,我不能真正遵循所有这些代码的目的(至少)来有一个明确的意见。我认识一些来自TC1/SC22/WG21 n2661 的命名。无论如何,我稍后会回到计算机上,看看将stopwatch隔离到自己的项目中是否会影响此错误的发生。

编辑 2

我把代码放到一个空项目中,问题依旧。作为补充说明,对于三个 to_*seconds 调用,有六个编译器错误。如果我把便捷方法放到 cmets 中,代码就可以编译运行了。

嗯,我想知道什么是好的解决方法(或修复)..?

【问题讨论】:

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


    【解决方案1】:

    我认为编译时错误是由于 Visual Studio 2012 RC 中的这个错误:

    https://connect.microsoft.com/VisualStudio/feedback/details/752794/std-chrono-duration-cast-lacks-double-support

    要解决此问题,请使用基于整数类型而不是浮点的持续时间:

    #include <cstdint>
    //...
    typedef std::chrono::duration<std::uint64_t, period> duration;
    

    【讨论】:

    • 确实,这就是原因。我看到您也将此提交给 MS Connect,也非常感谢!
    • Microsoft Visual Studio Premium 2012 Version 11.0.61219.00 Update 5 在这里。好像还在……
    【解决方案2】:

    如果我添加,您的代码将为我编译:

    #include <chrono>
    

    到它。我无权访问 Visual Studio 2012 RC,因此无法调查此错误的原因,甚至无法确定它发生在哪里。

    【讨论】:

    • 嗨!我稍微编辑了这个问题以包含更多细节。我在所有文件中都包含
    猜你喜欢
    • 1970-01-01
    • 2020-02-06
    • 1970-01-01
    • 1970-01-01
    • 2022-12-02
    • 2018-09-11
    • 1970-01-01
    • 1970-01-01
    • 2022-10-04
    相关资源
    最近更新 更多