C语言中怎么实现位操作
创始人
2024-12-25 18:02:35
0次

  C语言中提供了&(与)、|(或)、^(异或)、~(取反)、>>(右移)、<<(左移)6种位操作符。我们可以在程序中合理地使用这些位操作符号来提高程序的运行效率,例如,对于下面的示例代码:   intx=0;   inty=0;   x=257/8;   y=456%32;

我们可以通过位操作符将其修改成如下形式:

  intx=0;

  inty=0;

  x=257>>3;

  y=456-(456>>4<<4);   这样就可以使程序在性能上得到一定提升。   尽量避免对未知的有符号数执行位操作   在C语言中,如果在未知的有符号数上执行位操作,很可能会导致缓冲区溢出,从而在某些情况下导致攻击者执行任意代码,同时,还可能会出现出乎意料的行为或编译器定义的行为。   下面来看一个简单的示例:   #include

  intmain(void)

  {

  intx=0;

  inty=0x80000000;

  charbuf[sizeof("128")];

  x=sprintf(buf,"%u",y>>24);

  if(x==-1||x>=sizeof(buf))

  {

  //错误处理

  }

  printf(buf);

  return0;

  }

  代码中,y>>24的执行结果为4294967168,而sizeof(buf)的结果为4。当我们将y>>24的结果值转换为字符串“4294967168”时,超出了buf范围,所以结果值无法完全存储在buf中。因此,在执行语句“x=sprintf(buf,"%u",y>>24)”时,sprintf方法在进行写操作时就会越过buf的边界,从而产生缓冲区溢出。

  如果在编译器VC++中执行这段程序,将会产生错误报告。

  在C99中,要修正这样的错误,最好利用snprintf方法来代替sprintf方法。因为snprintf方法最多从源串中复制n-1个字符到目标串中,然后再从后面加一个0。因此,如果目标串的大小为n,将不会产生溢出。

当然,如果将变量y声明成为无符号类型

  即将:

  inty=0x80000000;

  修改为:

  unsignedinty=0x80000000;

  那么这种缓冲区溢出错误将不会发生。

  在右移中合理地选择0或符号位来填充空出的位

  在右移运算中,空出的位用0还是符号位进行填充呢?

  其实答案由具体的C语言编译器实现来决定。在通常情况下,如果要进行移位的操作数是无符号类型的,那么空出的位将用0进行填充;如果要进行移位的操作数是有符号类型的,则C语言编译器实现既可选择0来进行填充,也可选择符号位进行填充。

  因此,如果很关心一个右移运算中的空位,那么可以使用unsigned修饰符来声明变量,这样空位都会被设置为0。同时,如果一个程序采用了有符号数的右移位操作,那么它就是不可移植的。

  移位的数量必须大于等于0且小于操作数的位数

  如果被移位的操作数的长度为n,那么移位的数量必须大于等于0且小于n。因此,在一次单独的操作中不可能将所有的位从变量中移出。例如,一个int型的整数是32位,并且n是一个int型整数,那么n<<31和n<<0是合法的,但n<<32和n<<-1是不合法的。因此,我们在进行移位运算的时候必须做相关测试。示例代码如下所示: y="">=sizeof(unsignedint)*CHAR_BIT)

  {

  //错误处理

  }

  else

  {

  result=x>>y;

  }

  这里还需要说明的是,对于变量x与y,C99规定:

  对于x>y,如果x是无符号类型或非负值的有符号类型,那么x>>y的移位结果为x/2y的商的整数部分;如果x是有符号类型的负值,那么x>>y的移位结果是由编译器所定义的。因此,对一个带符号整数进行右移运算和将它除以2的某次幂不一定是等价的。要证明这一点很容易,考虑(-1)>>1的值,它的执行结果不可能为0,而在大多数C语言编译器中(-1)/2的结果都是0。

尽量避免在同一个数据上执行位操作与算术运算

  虽然位操作在很大程度上可以提高程序的执行效率,但在同一个变量上执行位操作和算术运算会模糊程序员的意图,削弱代码的可移植性与可读性,还会导致安全审核员或代码维护人员难以确定应该执行什么检查以消除安全缺陷,保证数据的完整性。

相关内容

热门资讯

空调连续工作多久需要停机休息 空调连续工作的时间取决于多个因素,包括空调的型号、功率、使用环境和维护情况等。一般来说,空调可以连续...
空调哪个符号是除湿的 空调除湿功能通常用一个水滴形状的符号表示。不同品牌和型号的空调遥控器可能会有所差异,但一般来说,除湿...
格力空调多长时间加一次氟利昂 1、一般情况下,空调对氟利昂的使用量是非常小的,所以在空调使用了四年左右的时候再考虑加也没问题。2、...
空调用多长时间需要加氟一次 一般情况下是五年。当出现以下这几种情况时,空调才需要加氟。1、空调的室内机和室外机各有两个接口,当接...
格调生活·C标思享荟:卡萨帝在... 9月12日的郑州龙湖金融岛,夜风轻拂,灯光璀璨。“C标时刻共传奇——卡萨帝思享荟暨20周年品牌盛典郑...
品牌价值破千亿、高端份额持续领... 9月12日,“C标时刻共传奇——卡萨帝思享荟暨20周年品牌盛典郑州站”在郑州龙湖金融岛举办。2026...
空调主板坏了修800还是换新的 空调主板坏了是修还是换新,需要考虑多个因素,以下是一些建议:1. 维修成本:如果维修费用较低,比如 ...
空调开多久需要休息多长时间 问题:空调开多久需要休息多长时间回答:1、在使用空调的过程中,一般空调开7~8个小时左右需要休息2~...
中央空调多长时间清洗一次 1、一般空调开机前清洗一次即可,空调开机中间时段再清洗一次,空调关机时清洗一次,这样比较合理。2、空...
中央空调氟利昂多久加一次 看空调制热和制冷程度,很多人的观点认为氟利昂必须一年放一次,其实这个观点是错误的,理解上面有点偏差,...