我们有uniform_int_distribution
和uniform_real_distribution
,有没有可能包含uniform_distribution
,专门在float/double和int/...指定时?为什么没有uniform_distribution?
回答
AFAIU,上面的评论由@ user877329和@revolver_ocelot解释正确,而另一个答案是完全错误的。
这是错误的,统一的uniform_int
和uniform_real
的接口,而不是因为它们是不同的方式实现(这可以通过模板特来解决),但由于接口意味着不同的事情。
假设我们统一接口(使用其他答案的建议的变化),像这样:
template <typename T>
using uniform_distribution =
typename std::conditional<
std::is_integral<T>::value,
std::uniform_int_distribution<T>,
std::uniform_real_distribution<T>
>::type;
那么,如果我们定义uniform_distribution<some_type> u(0, 9)
,意义是完全不同的:
如果
some_type
是整数,那么u将输出9大约1/10的时间。如果
some_type
不是,则u
将从未输出9.
下面的代码(其输出为true
然后false
)说明这一点:
#include <random>
#include <iostream>
#include <type_traits>
template <typename T>
using uniform_distribution =
typename std::conditional<
std::is_integral<T>::value,
std::uniform_int_distribution<T>,
std::uniform_real_distribution<T>
>::type;
int main()
{
std::random_device rd;
std::mt19937 gen(rd());
{
uniform_distribution<int> u(0, 9);
bool over_found = false;
for(size_t i = 0; i < 99999; ++i)
over_found = over_found || u(gen) >= 9;
std::cout << std::boolalpha << over_found << std::endl;
}
{
uniform_distribution<float> u(0, 9);
bool over_found = false;
for(size_t i = 0; i < 99999; ++i)
over_found = over_found || u(gen) >= 9;
std::cout << std::boolalpha << over_found << std::endl;
}
}
此代码说明使用这个类编写通用代码是危险的。例如,如果您要编写一个通用函数来计算子范围中的结果直方图:[0,1],[1,2,...,[8,9),结果将不兼容。
作为@revolver_ocelot指出,标准库的[inclusive-begin, exclusive_end) convention不能用于均匀整数(因为这将是不可能指定一个均匀的整数随机数生成器生成也最大UINT值),使之成为一个特殊的签名。
包容性或排他性的范围没有区别,因为无论如何,获得特定实数的概率(例如9)总是为0,因此从未看到预期的9。在数学意义上,双打和浮点数并不是真正的数字,但考虑到我们正在讨论随机数和浮点数,浮点数只是可以忽略不计的,浮点数和双精度对于实数而言只是近似值。 – nwp
@nwp因此,我也对绘制直方图的泛函功能发表了评论。即使像数学一样的实数,一个事件如* [8,9)*的概率肯定是非零的。不幸的是,由于这些事件的联合,标准库类型仓将留下不可忽视的部分结果。从实际意义上说,这些签名是不同的。 –
@nwp:“得到某个特定实数的概率,例如9,总是0” - 这是不真实的,因为尽管“uniform_real_distribution”这个名字不是实数上的连续分布。它是由“RealType”(默认为“double”)表示的有理数的有限子集上的离散分布。包括或排除端点因此*确实会有所作为。 –
- 1. 为什么Me.components什么都没有?
- 2. 为什么我的课没有什么?
- 3. 为什么gridview.selectedColumns什么都没有?
- 4. 为什么没有java.lang.UnsupportedClassVersionError?
- 5. 为什么没有asyncContext.cancel()
- 6. 为什么没有SortedList
- 7. 为什么Java没有宏?
- 8. 为什么没有UTF-24?
- 9. 为什么UDP没有“accept()”?
- 10. 为什么没有InterlockedExchangeSubtract64?
- 11. 为什么current_user没有?
- 12. 为什么没有ConfigurationManager?
- 13. 为什么没有Dictionary.TrimExcess()?
- 14. 为什么没有dscanf()?
- 15. 为什么没有启用
- 16. 为什么没有输出?
- 17. ModelState.AddModelError为什么没有ModelState.AddModelSuccess?
- 18. 为什么没有NSHTTPURLProtocol类?
- 19. 为什么Scala没有decltype?
- 20. WCF - 为什么没有WSDL
- 21. xActiveDirectory没有cmdlet。为什么?
- 22. 为什么没有std :: inplace_merge_unique?
- 23. 为什么没有String#shift()?
- 24. 为什么没有Math.floor(float)?
- 25. 没有屎树,为什么?
- 26. 为什么没有std :: from_string()?
- 27. 为什么datetime.time没有astimezone?
- 28. 为什么没有记录?
- 29. 为什么没有NSOperationWithBlock
- 30. 为什么我没有xlrd?
有一个想法:uniform_int_distribution使用了一个封闭的区间,uniform_real_distribution使用了一个半开放的区间。 – user877329
难道你不能定义你自己的结构并且专门化它吗?这确实很微不足道。 – skypjack
@AmiTavory [参考](http://en.cppreference.com/w/cpp/numeric/random/uniform_int_distribution)不同意。否则,你将无法获得INT_MAX和类似的。编辑:标准不同意,在'[rand.dist.uni.int]'它说:_A'uniform_int_distribution'随机数分布产生随机整数i,a <= i <= b_ –