使无符号整数下溢会引发异常

use*_*269 2 c++

我知道有些应用程序使用无符号整数上/下溢是获得廉价模运算的好方法.

在我的代码中,我uint专门用于容器的索引,所以我从不想要这种行为.

  1. 这是一个坏主意吗?我应该int在所有地方使用吗?我必须做一些令人讨厌的事情才能让for循环倒数到0.

  2. 是否有常用的不安全的无符号整数类型的实现?抛出异常的东西?

  3. 编译器(对我来说是gcc,clang)是否为给定编译单元中的不安全行为提供了一种机制?

Lig*_*ica 5

首先,一个术语狡辩:没有无符号整数下溢这样的东西,正是因为它们缠绕的方式(使用模运算),这可能是你的意思.

其次,这是一个常见的场景吗?是的,有点儿.你并不是唯一一个用反向计数循环做"令人厌恶的事情"的人,我打赌那里有很多人都没有做过"令人厌恶的事情"的错误,因此,他们的代码有一个令人讨厌的东西.隐藏在其中的无限循环.请注意,我不确定我是否会将无条件称为"不安全"的结果; 像任何东西一样,它们是无限可能工作子集的正确工具,并且在该子集中它们非常安全.

关于是否应该将无符号整数用于数组索引存在争议.一些标准委员会成员认为他们在标准库中的使用是错误的; 我知道Stack Overflow上的社区的几个成员也讨厌unsigned价值观并希望它们消失.

就个人而言,我认为默认情况下访问整数范围绝对是至关重要的(对于单个"-1"哨兵值或其他任何东西而言,失去它是不值得的)所以我认为 - 虽然你并不孤单这个要求,这是一个明智的要求 - 默认使用无符号数组索引是一件好事.(还有什么是负数组索引?语义,人!)

但在这种情况下,这对您没有帮助.所以你能对它做点啥?不,没有陷阱无符号整数实现(至少,不是我所知道的,更不用说普遍存在),因为这实际上违反了C++定义的类型规则:它会引入明确定义的下溢/溢出语义到甚至不可能出现下溢/溢出的类型.

你将不得不使用符号整数,并检查"逻辑下溢"(即外出的所期望的范围,比如-1)自己.您可以将此行为包装在类中.

我想你可能实际上只是换一个无符号整数,而你在它,添加一些额外的逻辑operator--operator-=检测环绕,并抛出.

但我想我的观点是,无论你做什么,它都会出现在你的"代码空间"中,从而导致性能下降.您无法从平台本身中剔除此行为.