[英]Boost ICL, cardinality of an interval set
In Boost ICL, when I call cardinality() or size() functions on an interval set, the return type is size_t, independent of the type of interval. 在Boost ICL中,当我在间隔集上调用cardinality()或size()函数时,返回类型是size_t,与间隔类型无关。 On 32-bit machines this is a 32-bit unsigned integer.
在32位机器上,这是一个32位无符号整数。 If my intervals, however, are of type int64_t, the cardinality can easily overflow the 32-bit integer.
但是,如果我的间隔是int64_t类型,则基数很容易溢出32位整数。 Am I missing something obvious here or is this a serious flaw of this library?
我错过了一些明显的东西,或者这是这个图书馆的一个严重缺陷?
EDIT: example added 编辑:示例添加
The following code compiles and runs without error on 64-bit but not on 32-bit machines, where it throws the assertion. 以下代码在64位上编译并运行时没有错误,但在32位计算机上没有错误,它会抛出断言。
#include <boost/icl/interval_set.hpp>
int main()
{
boost::icl::interval_set<int64_t> is;
is.add(boost::icl::interval<int64_t>::closed(1, 4294967297LL));
assert(boost::icl::cardinality(is) == 4294967297LL);
}
EDIT: I'm using boost::icl version 1.49.0 on Ubuntu 13.10 编辑:我在Ubuntu 13.10上使用boost :: icl版本1.49.0
EDIT: 编辑:
This is not particularly a 32/64-bit problem, as the following code wouldn't work on 64-bit either 这不是特别是32/64位问题,因为以下代码也无法在64位上运行
#include <boost/icl/interval_set.hpp>
int main()
{
boost::icl::interval_set<double> is;
is.add(boost::icl::interval<double>::closed(1, 1.5));
assert(boost::icl::cardinality(is) == 0.5);
}
Reproduced with Boost 1_54 on Ubuntu 14.04.1 LTS 在Ubuntu 14.04.1 LTS上使用Boost 1_54重现
This indeed seems to be a bug. 这确实是一个错误。 The specialization to fix is
修复的专业是
template <class Type>
struct get_size_type<Type, false, false, false>
{
typedef std::size_t type;
};
In icl/type_traits/size_type_of.hpp
. 在
icl/type_traits/size_type_of.hpp
。 Somehow the ICL devs appear not to be testing with -m32 these days. 不知何故,这些天ICL开发人员似乎没有使用-m32进行测试。
I've had success replacing it by 我已成功取代它
// BEGIN SEHE WAS HERE
template <class Type>
struct get_size_type<Type, std::enable_if<not boost::is_arithmetic<Type>::value, mpl::false_>::type::value, false, false>
{
typedef std::size_t type;
};
template <class Type>
struct get_size_type<Type, std::enable_if<boost::is_arithmetic<Type>::value, mpl::false_>::type::value, false, false>
{
typedef typename std::common_type<Type, std::size_t>::type type;
};
// END SEHE WAS HERE
The trait is sadly not very SFINAE friendly, hence the hack to use the first bool
template argument for SFINAE. 可悲的是,这个特性并不是非常友好的SFINAE,因此使用SFINAE的第一个
bool
模板参数的黑客。 Improvements could be: 改进可能是:
boost
type traits only boost
类型特征 common_type<...>
for integral types common_type<...>
I've tested this to DoTheRightThing(TM) for interval_set<double>
as well as interval_set<uint64_t>
on g++ -m32 and -m64. 我已经在for ++设置了对于
interval_set<double>
DoTheRightThing(TM)以及对g ++ -m32和-m64的interval_set<uint64_t>
。
I'd report this on the mailing list. 我会在邮件列表上报告这个问题。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.