通常在我的内部循环中,我需要以"环绕"方式索引数组,因此如果数组大小为100并且我的代码要求元素-2,则应该给出元素98.在许多高级语言中作为Python,人们可以简单地使用my_array[index % array_size],但由于某种原因,C的整数运算(通常)向零舍入而不是一致向下舍入,因此当给定负的第一个参数时,其模运算符返回负结果.
通常我知道这index不会少于-array_size,在这些情况下我只是这样做my_array[(index + array_size) % array_size].但是,有时这无法得到保证,对于那些情况,我想知道实现始终为正模数函数的最快方法.有几种"聪明"的方法可以在没有分支的情况下完成,例如
inline int positive_modulo(int i, int n) {
return (n + (i % n)) % n;
}
Run Code Online (Sandbox Code Playgroud)
要么
inline int positive_modulo(int i, int n) {
return (i % n) + (n * (i < 0));
}
Run Code Online (Sandbox Code Playgroud)
当然,我可以对这些进行分析,以找出哪个是我系统中最快的,但我不禁担心我可能错过了一个更好的,或者我的机器上的速度可能在另一个机器上很慢.
那么有没有一种标准的方法可以做到这一点,或者一些我错过的聪明技巧可能是最快的方式?
此外,我知道这可能是一厢情愿的想法,但如果有一种方法可以自动矢量化,那将是惊人的.
我试图弄清楚算术位移运算符在C中是如何工作的,以及它将如何影响带符号的32位整数.
为简单起见,假设我们在一个字节(8位)内工作:
x = 1101.0101
MSB[ 1101.0101 ]LSB
Run Code Online (Sandbox Code Playgroud)
在Stack Overflow和一些网站上阅读其他帖子,我发现:
<<将转向MSB(在我的情况下向左),并用0填充"空"LSB位.
而>>会向着转向LSB(向右,在我的情况),并填写"空"与MS位位
因此,x = x << 7将导致LSB移动到MSB,并将所有内容设置为0.
1000.0000
Run Code Online (Sandbox Code Playgroud)
现在,让我说我会>> 7,最后的结果.这会导致[0000.0010]?我对吗?
关于转移运营商我的假设是对的吗?
我刚在我的机器上测试过,**
int x = 1; //000000000......01
x = x << 31; //100000000......00
x = x >> 31; //111111111......11 (Everything is filled with 1s !!!!!)
Run Code Online (Sandbox Code Playgroud)
为什么?
我正在尝试分配:"在不使用sizeof()函数的情况下查找无符号整数数据类型中的位数."
我的设计是将整数转换为位然后计算它们.对于前:10 is 1010和5 is 101
将整数转换为位表示形式显示如下:
do
{
Vec.push_back( x & 1 )
}
while ( x >>= 1 );
Run Code Online (Sandbox Code Playgroud)
我不想只是复制粘贴的东西.当我使用F-10时,我看到(x & 1)正在做什么,但我不知道它是名字还是它如何完成它的工作(比较一些东西?).我也知道>=哪个"大于或等于"但是什么x >>= 1?
注意:标记的副本是JavaScript而不是C++
c++ bit-manipulation bit-shift bitwise-operators bitwise-and
以下程序
#include <inttypes.h> /* printf(" %" PRIu32 "\n"), my_uint32_t) */
#include <stdio.h> /* printf(), perror() */
int main(int argc, char *argv[])
{
uint64_t u64 = ((unsigned char)0x80) << 24;
printf("%" PRIX64 "\n", u64);
/* uint64_t */ u64 = ((unsigned int)0x80) << 24;
printf("%016" PRIX64 "\n", u64);
}
Run Code Online (Sandbox Code Playgroud)
产生
FFFFFFFF80000000
0000000080000000
Run Code Online (Sandbox Code Playgroud)
是什么区别((unsigned char)0x80),并((unsigned int)0x80)在这方面?
我想这(unsigned char)0x80会被提升到(unsigned char)0xFFFFFFFFFFFFFF80然后有点转移,但为什么这种转换认为unsigned char是签名?
值得注意的是,它0x80 << 16会产生预期的结果0x0000000000800000.
给定std::bitset<64> bits任意数量的位和位位置X(0-63)
在X位或更低位计数位的最有效方法是什么,如果未设置X位,则返回0
注意:如果设置该位,则返回始终至少为1
蛮力方式很慢:
int countupto(std::bitset<64> bits, int X)
{
if (!bits[X]) return 0;
int total=1;
for (int i=0; i < X; ++i)
{
total+=bits[i];
}
return total;
}
Run Code Online (Sandbox Code Playgroud)
这个count()方法bitset将为您popcount提供所有位,但bitset不支持范围
注意:这不是如何计算32位整数中的设置位数?因为它询问所有位而不是0到X的范围
我使用Visual Studio,Ubuntu的GCC,英特尔编译器,MinGW测试了右移.所有移位的符号位.我猜Xcode的GCC也是如此.
我知道这种行为是特定于实现的,但看起来所有主要的桌面/服务器编译器都实现了算术移位.是否有任何广泛使用的编译器不会在符号位中移位?
谢谢.
在下面的代码中
int main()
{
int a = -1;
printf("%d",a>>1);
return 0;
}
Run Code Online (Sandbox Code Playgroud)
为什么它给出输出-1.
我想要得到的价值INT_MIN和INT_MAX,和我试过~0和~0 >> 1,因为最左边的位为符号位.我得到了他们两个-1.
它太混乱了,为什么不~0成为0xffffffff和~0 >> 1将来0x7fffffff?
-5 / 2 = -2
-5 >> 1 = -3
Run Code Online (Sandbox Code Playgroud)
我向老师学习>> 1将数字除以2.它对正数有效,但对负数不起作用.有人可以向我解释一下吗?
谢谢
赫伯特·希尔特(Herbert Schildt)的书"C完整参考文献"中说"(在有符号的负整数的情况下,右移将导致1被引入,以便保留符号位.)"
保留标志位有什么意义?
此外,我认为这本书是指使用符号位表示负数而不使用二进制补码的情况.但即使在这种情况下,推理似乎也没有任何意义.