gpt4 book ai didi

c++ - 在编译时选择随机数分布

转载 作者:太空狗 更新时间:2023-10-29 20:01:49 26 4
gpt4 key购买 nike

我正在使用 TYPED_TEST 编写测试谷歌测试的功能,它允许我将测试概括为多种类型。我正在测试 int 类型的类模板和 double .在测试中,我需要生成随机数。为此,我尝试使用 std::uniform_int_distribution<T>std::uniform_real_distribution<T>但遇到了静态断言。

顾名思义, std::uniform_int_distribution<T> 检查是否 T是整数类型, std::uniform_real_distribution<T> 检查 T是浮点型。

由于我的测试会自动测试 int然后是 double ,我一直在尝试编写某种函数,使我能够在编译时为类型选择正确的分布。更准确地说,是这样的:

template<class T>
Distribution get_right_distribution(const T& a, const T& b)
{
if(T is integral) // Compile time is needed, runtime
// fails since both if and else have to compile
{
return std::uniform_real_distribution(a, b);
}
else
{
return std::uniform_real_distribution(a, b);
}
}

请注意,这只是我一直在尝试做的伪代码。这种逻辑分支失败是因为 ifelse必须编译。

我已经对如何做到这一点做了一些研究,我觉得 std::is_integral<T>std::is_floating_point<T>是解决方案的一部分,但到目前为止我还无法编译任何东西。我主要尝试了两件事:

  1. 使用模板特化来缩短编译时间。
  2. 使用enable_if .

使用第一种方法,我得到了一条错误消息,告诉我我的重载不明确。使用第二种方法,我尝试了一些东西,但迷失在它导致的令人讨厌的语法中(至少对于不习惯它的人来说)。

您对如何实现这一点有什么建议吗?

附言我想看看如何做到这一点,所以将我的测试分成两部分对我来说不是一个可以接受的答案。

最佳答案

C++17

我可能会使用 C++17,你可以使用 if constexpr(...) :

#include <iostream>
#include <random>
#include <type_traits>

template <typename T>
auto get_right_distribution(const T a, const T b) {
if constexpr(std::is_integral<T>::value) {
return std::uniform_int_distribution(a, b);
}
else {
return std::uniform_real_distribution(a, b);
}
}

int main() {
std::random_device rd;
std::mt19937 gen(rd());

auto int_dis = get_right_distribution(1, 6);
std::cout << int_dis(gen) << "\n";

auto float_dis = get_right_distribution(1.F, 6.F);
std::cout << float_dis(gen) << "\n";
}

C++11 和 C++14

对于 C++11 和 C++14,您可以在模板参数列表中使用有条件的额外模板类型参数来选择返回类型和分布。

C++11:

template <typename T,
typename Distribution = typename std::conditional<
std::is_integral<T>::value,
std::uniform_int_distribution<T>,
std::uniform_real_distribution<T>>::type>
Distribution get_right_distribution(const T a, const T b) {
return Distribution(a, b);
}

C++ 14(由 auto 推导的返回类型,并使用 std::conditional_t 帮助器类型的缩写形式 std::conditional<...>::type ):

template <typename T,
typename Distribution = typename std::conditional_t<
std::is_integral<T>::value,
std::uniform_int_distribution<T>,
std::uniform_real_distribution<T>>>
auto get_right_distribution(const T a, const T b) {
return Distribution(a, b);
}

关于c++ - 在编译时选择随机数分布,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/52021277/

26 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com