如何将std::chrono::duration作为C++函数参数传递?
std::chrono::duration作为函数参数传递的问题
问题代码
#include <chrono> #include <iostream> #include <thread> // 此处报错 void foo(const std::chrono::duration& d) { std::cout << d.count() << std::endl; } int main() { const auto s = std::chrono::steady_clock::now(); std::this_thread::sleep_for(std::chrono::seconds(3)); const auto e = std::chrono::steady_clock::now(); // 此处无报错 const std::chrono::duration d = e - s; std::cout << d.count() << std::endl; }
错误信息
<source>:5:10: error: missing template argument list after 'std::chrono::duration'; template placeholder not permitted in parameter 5 | void foo(const std::chrono::duration& d) { | ^~~~~ | <> <source>:5:10: note: or use 'auto' for an abbreviated function template In file included from /cefs/38/383ad2f84cbd57a52fd68bbe_consolidated/compilers_c++_x86_gcc_16.1.0/include/c++/16.1.0/chrono:51, from <source>:1: /cefs/38/383ad2f84cbd57a52fd68bbe_consolidated/compilers_c++_x86_gcc_16.1.0/include/c++/16.1.0/bits/chrono.h:68:13: note: 'template<class _Rep, class _Period> class std::chrono::duration' declared here 68 | class duration; | ^~~~~~~~ <source>: In function 'void foo(...)': <source>:6:18: error: 'd' was not declared in this scope 6 | std::cout << d.count() << std::endl; | ^ Compiler returned: 1
原因分析
std::chrono::duration是模板类,定义为template<class _Rep, class _Period> class duration;,必须指定模板参数才能使用:
- main函数中
const std::chrono::duration d = e - s;能编译,是因为C++17引入的类模板实参推导(CTAD):编译器可以从e - s的结果(steady_clock::duration类型)自动推导duration的模板参数。 - 但函数参数列表不支持这种自动推导,直接写
std::chrono::duration&相当于使用未实例化的模板,编译器无法识别具体类型,因此报错。
解决方法
方法1:使用模板函数,让编译器推导参数
将foo定义为模板函数,编译器会根据传入的实参自动推导duration的模板参数:
#include <chrono> #include <iostream> #include <thread> template<typename Rep, typename Period> void foo(const std::chrono::duration<Rep, Period>& d) { std::cout << d.count() << std::endl; } int main() { const auto s = std::chrono::steady_clock::now(); std::this_thread::sleep_for(std::chrono::seconds(3)); const auto e = std::chrono::steady_clock::now(); const std::chrono::duration d = e - s; foo(d); // 自动推导模板参数 }
方法2:指定具体的模板参数
如果你只需要处理特定类型的duration(比如steady_clock返回的时长类型),可以直接指定模板参数:
#include <chrono> #include <iostream> #include <thread> // 使用steady_clock的duration类型 void foo(const std::chrono::steady_clock::duration& d) { std::cout << d.count() << std::endl; } int main() { const auto s = std::chrono::steady_clock::now(); std::this_thread::sleep_for(std::chrono::seconds(3)); const auto e = std::chrono::steady_clock::now(); const std::chrono::duration d = e - s; foo(d); }
方法3:用auto作为函数参数(C++20及以上)
C++20支持缩写函数模板,用auto代替模板参数,写法更简洁:
#include <chrono> #include <iostream> #include <thread> void foo(const auto& d) { std::cout << d.count() << std::endl; } int main() { const auto s = std::chrono::steady_clock::now(); std::this_thread::sleep_for(std::chrono::seconds(3)); const auto e = std::chrono::steady_clock::now(); const std::chrono::duration d = e - s; foo(d); }
内容的提问来源于stack exchange,提问作者Harry
相关产品推荐
相关产品推荐

