40

我正在使用 c++11<chrono>并且有许多秒数表示为双精度数。我想在这段时间内使用 c++11 休眠,但我无法理解如何将其转换为需要的std::chrono::duration对象std::this_thread::sleep_for

const double timeToSleep = GetTimeToSleep();
std::this_thread::sleep_for(std::chrono::seconds(timeToSleep));  // cannot convert from double to seconds

我已经锁定了<chrono>参考,但我发现它相当混乱。

谢谢

编辑:

以下给出错误:

std::chrono::duration<double> duration(timeToSleep );
std::this_thread::sleep_for(duration);

错误:

c:\program files (x86)\microsoft visual studio 11.0\vc\include\chrono(749): error C2679: binary '+=' : no operator found which takes a right-hand operand of type 'const std::chrono::duration<double,std::ratio<0x01,0x01>>' (or there is no acceptable conversion)
2>          c:\program files (x86)\microsoft visual studio 11.0\vc\include\chrono(166): could be 'std::chrono::duration<__int64,std::nano> &std::chrono::duration<__int64,std::nano>::operator +=(const std::chrono::duration<__int64,std::nano> &)'
2>          while trying to match the argument list '(std::chrono::nanoseconds, const std::chrono::duration<double,std::ratio<0x01,0x01>>)'
2>          c:\program files (x86)\microsoft visual studio 11.0\vc\include\thread(164) : see reference to function template instantiation 'xtime std::_To_xtime<double,std::ratio<0x01,0x01>>(const std::chrono::duration<double,std::ratio<0x01,0x01>> &)' being compiled
2>          c:\users\johan\desktop\svn\jonsengine\jonsengine\src\window\glfw\glfwwindow.cpp(73) : see reference to function template instantiation 'void std::this_thread::sleep_for<double,std::ratio<0x01,0x01>>(const std::chrono::duration<double,std::ratio<0x01,0x01>> &)' being compiled
4

5 回答 5

34

不要做std::chrono::seconds(timeToSleep)。你想要更多类似的东西:

std::chrono::duration<double>(timeToSleep)

或者,如果timeToSleep不是以秒为单位,您可以将比率作为模板参数传递给duration. 有关更多信息,请参见此处(以及那里的示例)。

于 2013-07-27T16:01:18.367 回答
6

使@Cornstalks 的答案更加通用,您可以定义如下函数:

template <typename T>
auto seconds_to_duration(T seconds) {
    return std::chrono::duration<T, std::ratio<1>>(seconds);
}

这会将任何原始类型的秒值转换为计时持续时间。像这样使用它:

const double timeToSleep = GetTimeToSleep();
std::this_thread_sleep_for(seconds_to_duration(timeToSleep));
于 2018-06-19T10:53:14.453 回答
4
const unsigned long timeToSleep = static_cast<unsigned long>( GetTimeToSleep() * 1000 );
std::this_thread::sleep_for(std::chrono::milliseconds(timeToSleep));
于 2013-07-27T16:01:00.627 回答
0
std::chrono::milliseconds duration(timeToSleep);
std::this_thread::sleep_for( duration );
于 2013-07-27T16:04:04.107 回答
0

以上都不适合我。发现工作解决方案是对另一个问题的回答:

从双秒到 std::chrono::steady_clock::duration 的简洁转换?

double period_in_seconds = 3.4;

auto as_duration = std::chrono::duration_cast<std::chrono::steady_clock::duration>(std::chrono::duration<double>(period_in_seconds));

这会将 a 转换double为 a std::chrono::steady_clock::duration

通常,在使用标准时钟时,例如steady_clock,您的持续时间变量应该始终是该时钟的成员类型,例如std::chrono::steady_clock::duration.

避免从模板创建您自己的持续时间类型,例如std::chrono::duration<double>,除了临时使用 with duration_cast,如上所示。

这使得时间比较std::chrono::steady_clock::now()最快,因为它避免了在运行时不必要的转换,因为变量的持续时间类型已经与time_point返回的持续时间类型匹配now()

于 2021-03-09T07:51:27.190 回答