【C语言之】二进制的移位运算

ops/2024/12/23 9:09:44/

【C语言之】二进制的移位运算

1、左移运算 <<

  • 二进制左移运算符:<<,将操作数的所有位向左移动指定的位数。左移 n 位相当于乘以 2 的 n 次方。将一个运算对象的各二进制位全部左移若干位,左边的二进制位丢弃,右边补0。
  // #b0001 1001 << 2  //===> #b0110 0100

2、右移运算 >>

  • 二进制右移运算符:>>,将操作数的所有位向右移动指定的位数。右移n位相当于除以 2 的 n 次方。将一个数的各二进制位全部右移若干位,正数左补 0,负数左补 1,右边丢弃。
  // #b0001 1001 >> 2  //===> #b0000 0110  //无符号// #b1001 1001 >> 2  //===> #b1110 0110  //有符号

3、左移测试

  • 将值为1的字符型变量c,左移9次,循环输出结果,代码如下:
/* filename : wa.c */
#include <stdio.h>/* test shift left << function */
void
test_shift_left (void)
{char x = 1;for (int i = 0; i < 9; i++){char c = x << i;printf ("No.%d, [%3d]\n", i, c);}
}/**/
int
main (int argc, char *argv[])
{test_shift_left ();return 0;
}
//----- << -----//

4、编译运行,输出结果如下:

No.0, [  1]
No.1, [  2]
No.2, [  4]
No.3, [  8]
No.4, [ 16]
No.5, [ 32]
No.6, [ 64]
No.7, [-128]
No.8, [  0]

5、再修改一下

  • 左移0位,结果数值不变!
  • 左移7位,二进制为 #b1000 0000,左高右低,最高位为符号位,值变为-128!
  • 上面的结果说明:每左移一次,相当乘以2一次!
  • 将字符c改为无符号字符型,第11行修改成如下代码:
      unsigned char c = x << i;

6、编译运行,输出结果如下:

  • 改为无符号,所以左移7位值为128!
No.0, [  1]
No.1, [  2]
No.2, [  4]
No.3, [  8]
No.4, [ 16]
No.5, [ 32]
No.6, [ 64]
No.7, [128]
No.8, [  0]

7、循环判断一个字符的各二进制位是0还是1

  • 用上面的代码,在函数中定义一个字符变量n,赋值为0x74,二进制为:#b0111 0100
  • 将移位结果c与n进行按位与运算,如结果为0,说明当前位为0,如结果不为0,说明当前位为1!
  • 循环判断,输出结果,代码如下:
/* filename : wa.c */
#include <stdio.h>/* test shift left << function */
void
test_shift_left (void)
{char x = 1;char n = 0x74; //#b0111 0100for (int i = 0; i < 9; i++){unsigned char c = x << i;char r = n & c;printf ("No.%d, [%3d], [%d]\n", i, c, r);}
}/**/
int
main (int argc, char *argv[])
{test_shift_left ();return 0;
}
//----- << -----//

8、编译运行,输出结果如下:

No.0, [  1], [0]
No.1, [  2], [0]
No.2, [  4], [4]
No.3, [  8], [0]
No.4, [ 16], [16]
No.5, [ 32], [32]
No.6, [ 64], [64]
No.7, [128], [0]
No.8, [  0], [0]

9、用上面的结果来将一个字符转为二进制

  • 定义字符数组buf,长度为9,8个二进制字符加1个字符串结束符’\0’,数组初始化为0,也就是’\0’!
  • 左移是从右向左,从低位向高位;数组是相反的,从左向右!
  • 定义整型变量j,从7向0循环,对应buf[7]至buf[0],依次赋值!
  • 代码如下:
/* filename : wa.c */
#include <stdio.h>/* test shift left << function */
void
test_shift_left (void)
{char buf[9] = {0};char x = 1;char n = 0x74; //#b0111 0100for (int i = 0, j = 7; i < 8; i++, j--){unsigned char c = x << i;char r = n & c;printf ("No.%d, [%3d], [%d]\n", i, c, r);if (r != 0) buf[j] = '1';else        buf[j] = '0';}printf ("-------------------------\n");printf ("0x%X ===> [%s]\n", n, buf);
}/**/
int
main (int argc, char *argv[])
{test_shift_left ();return 0;
}
//----- << -----//

10、编译运行,输出结果如下:

No.0, [  1], [0]
No.1, [  2], [0]
No.2, [  4], [4]
No.3, [  8], [0]
No.4, [ 16], [16]
No.5, [ 32], [32]
No.6, [ 64], [64]
No.7, [128], [0]
-------------------------
0x74 ===> [01110100]

11、右移测试

  • 定义高位为1的字符型变量x,赋值为0x80,二进制为#b1000 0000
  • 定义字符型变量n,赋值为0x44,二进制为#b0100 0100
  • 测试字符n的各二进制位的情况,代码如下:
/* test shift right >> function */
void
test_shift_right (void)
{unsigned char x = 0x80; //#b1000 0000char n = 0x44; //#b0100 0100for (int i = 0; i < 8; i++){unsigned char c = x >> i;unsigned char r = n & c;printf ("No.%d, [%3d], [%d]\n", i, c, r);}
}/**/
int
main (int argc, char *argv[])
{//test_shift_left ();test_shift_right ();return 0;
}
//----- << & >> -----//

12、编译运行,输出结果如下:

No.0, [128], [0]
No.1, [ 64], [64]
No.2, [ 32], [0]
No.3, [ 16], [0]
No.4, [  8], [0]
No.5, [  4], [4]
No.6, [  2], [0]
No.7, [  1], [0]

13、输出字符变量的二进制格式字符串

  • 上面结果可以看出:每移位一次,相当于除以2一次!
  • 由于是从左至右,直接用for循环的i来索引buf保存即可!
  • 注意,将字符定义为无符号型,否则输出的是负数,或输出你意想不到的结果!
  • 这次测试的字符是0xF4,代码如下:
/* test shift right >> function */
void
test_shift_right (void)
{char buf[9] = {0};unsigned char x = 0x80; //#b1000 0000//char n = 0x44; //#b0100 0100unsigned char n = 0xF4; //#b1111 0100for (int i = 0; i < 8; i++){unsigned char c = x >> i;unsigned char r = n & c;printf ("No.%d, [%3d], [%d]\n", i, c, r);if (r != 0) buf[i] = '1';else        buf[i] = '0';}printf ("-------------------------\n");printf ("0x%X ===> [%s]\n", n, buf);
}

14、编译运行,基本达到预期,输出结果如下:

No.0, [128], [128]
No.1, [ 64], [64]
No.2, [ 32], [32]
No.3, [ 16], [16]
No.4, [  8], [0]
No.5, [  4], [4]
No.6, [  2], [0]
No.7, [  1], [0]
-------------------------
0xF4 ===> [11110100]

15、完整代码如下:

/* filename : wa.c */
#include <stdio.h>/* test shift left << function */
void
test_shift_left (void)
{char buf[9] = {0};char x = 1;char n = 0x74; //#b0111 0100for (int i = 0, j = 7; i < 8; i++, j--){unsigned char c = x << i;char r = n & c;printf ("No.%d, [%3d], [%d]\n", i, c, r);if (r != 0) buf[j] = '1';else        buf[j] = '0';}printf ("-------------------------\n");printf ("0x%X ===> [%s]\n", n, buf);
}/* test shift right >> function */
void
test_shift_right (void)
{char buf[9] = {0};unsigned char x = 0x80; //#b1000 0000//char n = 0x44; //#b0100 0100unsigned char n = 0xF4; //#b1111 0100for (int i = 0; i < 8; i++){unsigned char c = x >> i;unsigned char r = n & c;printf ("No.%d, [%3d], [%d]\n", i, c, r);if (r != 0) buf[i] = '1';else        buf[i] = '0';}printf ("-------------------------\n");printf ("0x%X ===> [%s]\n", n, buf);
}/**/
int
main (int argc, char *argv[])
{//test_shift_left ();test_shift_right ();return 0;
}
//----- << & >> -----//

http://www.ppmy.cn/ops/144264.html

相关文章

搜索排序:重排

重排 重排 是精排后的一个阶段&#xff0c;主要负责在最终展示结果前对精排后的排序列表进行进一步优化和调整&#xff08;微调&#xff09;。重排核心目标是保证一定相关性的前提下&#xff0c;提高结果的多样性&#xff0c;从而提升用户体验&#xff0c;满足用户在不同方面的…

力扣-图论-16【算法学习day.66】

前言 ###我做这类文章一个重要的目的还是给正在学习的大家提供方向和记录学习过程&#xff08;例如想要掌握基础用法&#xff0c;该刷哪些题&#xff1f;&#xff09;我的解析也不会做的非常详细&#xff0c;只会提供思路和一些关键点&#xff0c;力扣上的大佬们的题解质量是非…

渗透测试-前端加密分析之RSA加密登录(密钥来源服务器)

本文是高级前端加解密与验签实战的第6篇文章&#xff0c;本系列文章实验靶场为Yakit里自带的Vulinbox靶场&#xff0c;本文讲述的是绕过RSA加密来爆破登录。 分析 这里的代码跟上文的类似&#xff0c;但是加密的公钥是通过请求服务端获取的 http://127.0.0.1:8787/crypto/js/…

RunCam WiFiLink连接手机图传测试

RunCam WiFiLink中文手册从这里下载 一、摄像头端 1.连接天线&#xff08;易忘&#xff09; 2.打开摄像头前面的盖子&#xff08;易忘&#xff09; 3.接上直流电源&#xff0c;红线为正&#xff0c;黑线为负 4.直流电源设置电压为14v&#xff0c;电流为3.15A&#xff0c; 通…

007 Qt_按钮类控件

文章目录 前言push ButtonRadio ButtionCheck BoxToolButton 小结 前言 本文将会向你介绍按钮类控件的属性与使用 push Button QPushButton 表示⼀个按钮&#xff0c;QPushButton 继承自 QAbstractButton &#xff0c;这个类是⼀个抽象类. 是其他按钮的父类 在QAbstractBut…

iOS应用网络安全之HTTPS

1. HTTPS/SSL的基本原理 安全套接字层 (Secure Socket Layer, SSL) 是用来实现互联网安全通信的最普遍的标准。Web 应用程序使用 HTTPS&#xff08;基于 SSL 的 HTTP&#xff09;&#xff0c;HTTPS 使用数字证书来确保在服务器和客户端之间进行安全、加密的通信。在 SSL 连接中…

MONI后台管理系统-swagger3(springdoc-openapi)集成

springdoc-openapi Java 库有助于使用 Spring Boot 项目自动生成 API 文档。springdoc-openapi 通过在运行时检查应用程序来根据 Spring 配置、类结构和各种注释推断 API 语义。 该库会自动生成 JSON/YAML 和 HTML 格式的页面文档。生成的文档可以使用swagger-api注释进行补充。…

c4d动画怎么导出mp4视频,c4d动画视频格式设置

宝子们&#xff0c;今天来给大家讲讲 C4D 咋导出mp4视频的方法。通过用图文教程的形式给大家展示得明明白白的&#xff0c;让你能轻松理解和掌握&#xff0c;不管是理论基础&#xff0c;还是实际操作和技能技巧&#xff0c;都能学到&#xff0c;快速入门然后提升自己哦。 c4d动…