【位运算进阶之----右移(>>)】

😄嘻嘻,朋友们,大家好!昨天我们学习了左移,今天我们来谈谈右移>>。


⭐️简单来说,右移就是将一个数二进制表达整体向右移动,也就是去掉一个数的二进制表达的末位,右移一位就去掉一位,右移两位就去掉两位。一般情况下右移就是除以2的幂并向下取整。

下面就让我们来详细看看吧!

在这里插入图片描述


文章目录

  • 一、基础知识
    • 1️⃣ 右移的二进制表示:
    • 2️⃣ 右移的执行结果:
    • 3️⃣ 对负数右移:-x>>y=-⌈(x>>y)⌉(不建议用)
      • 1. -9>>1
      • 2. ((unsigned int)-9) >> 2
    • 4️⃣ 右移负数位:
  • 二、拓展应用:
    • 1. 去除低k位:
    • 2. 取第k位的值:
  • 三、写在后面的话:


一、基础知识

✨右移运算符是一个二元运算符,右移操作是也一种位操作,用来将一个数的二进制表达所有位向右移动指定的位数

✨我们知道,无符号整数都是非负数,所以负数只出现在有符号整数中。(所以我们这里可以不分有符号整数和无符号整数):

  • 对于正数直接右移(左侧添0,可视为不添)
  • 对于负数右移后左侧添1;0你懂的

1️⃣ 右移的二进制表示:

✨x>>y 表示将x的二进制表达向右移动y位(其中x和y都是整数)。
如:1001 >> 2 ----> 10 (直接去掉后两位)


2️⃣ 右移的执行结果:

✨右移操作相当于将一个数除以2的n次方
x>>y <=> [ x 2 y \frac {x}{2^y} 2yx] ,方括号一般认为是向下取整。咦?不是常说右移是除以2,左移是乘以2吗,你这怎么还向下取整了呢?
在这里插入图片描述
👉因为不是所有的数都能被2整除,所以根据C语言右移的规则,应当向下取整。(C语言除法结果是正数则向下取整,结果为负数则向零取整)
在这里插入图片描述

  • 所以上面的1001>>2 = [ 9 2 2 \frac {9}{2^2} 229] = [ 9 4 \frac {9}{4} 49] = 2(向下取整)

代码如下:

#include<stdio.h>int main(void)
{int a = 0b1001;unsigned int b = a ;printf("%d\n", a>>2);printf("%u\n", b>>2);return 0;
}

执行结果如下:

在这里插入图片描述
可以看出结果是9/4=2;
下面我们继续增大右移的位数:

#include<stdio.h>int main(void)
{int a = 0b1001;//9unsigned int b = a ;printf("%d\n", a>>4);printf("%u\n", b>>4);return 0;
}

在这里插入图片描述
可以看出9/16=0,没什么问题。

  • 当然,这里也可以从补码(移位)的角度来解释。9的二进制表达一共4位有效,向右移动4位后显然是0。

3️⃣ 对负数右移:-x>>y=-⌈(x>>y)⌉(不建议用)

注:-x>>y并不等于-(x>>y)

如:-9>>1 是多少呢?相信你心中已经有答案了,请看下图!

#include<stdio.h>int main(void)
{int a = -9;unsigned int b = a ;printf("%d\n", a >> 1);//	-9>>1printf("%d\n", a / 2);//	-9/2printf("%d\n", a>>2);//		-9>>2printf("%d\n", a >> 3);//	-9>>3printf("%u\n", b>>2);//		(unsigned int )-9>>2return 0;
}

执行结果如下:
在这里插入图片描述

我们先来看a,a是一个有符号整数-9,现在对其右移。

1. -9>>1

  • (1)值的角度:
    -9>>1 = [-9/2] = [-4.5] = -5 (向下取整),但-(9>>1)=-([9/2])=-4
    注意:这里千万要和-9/2 = -4区分开来!因为在C语言中,对于负数的取整通常是向零取整(向上取整)。也就是说,负数会被取整为最接近且大于等于它的整数。
    如:(int)(-3.9) = -3 ;(int)(-2.1) = -2;

对应的符合见下图,左面是向下取整,右面是向上取整:
在这里插入图片描述
下面是它们的图像:

❤️向下取整(高斯函数):
在这里插入图片描述
❤️向上取整:
在这里插入图片描述
这里我就不展开讨论了,以后有机会再深入去了解其二者的相关知识。

  • (2)补码的角度:
    • 9的补码是:00000000 00000000 0000000 00001001
    • -9的补码是:11111111 11111111 11111111 11110110 + 1-->11111111 11111111 11111111 11110111
    • -9的补码右移一位:11111111 11111111 11111111 11111011(左侧补1)
    • 转换成机器数(原码):10000000 00000000 00000000 00000100+1-->10000000 00000000 00000000 00000101 = -5

😄综上我们得到了-x>>y = -⌈(x>>y)⌉ = -(⌈ x 2 y \frac {x}{2^y} 2yx⌉),注意,此处是向上取整,但计算机中默认正整数除法是向下取整,所以你可能要用ceil函数自己处理。

-9>>2,-9>>3与上面的推理过程类似,此处不再赘述!


2. ((unsigned int)-9) >> 2

  • 现在,就让我们来看看上图的最后一个输出,为什么是1073741821呢?

在这里插入图片描述
✨首先,b的类型是unsigned int ,无符号整型,也就是都是非负的。现在我们执行第一个语句:b=a , 将-9赋值给一个无符号整型,b的值将会变成多少呢?这里我们借助昨天的图来进行求解:👇
在这里插入图片描述
✨如何求b的值,言下之意就是让我们从0开始往左数9个数,可以轻松得到b的值是2 ^ 32-9,也就是4294967296-9=4294967287
✨现在,我们得到了((unsigned int)-9) >> 2 <=> 4294967287>>2,下面从两个方面进行求解:

  • (1)值的角度:然后另b除以4并向下取整,即[4294967287/4]=4294967287/4=1073741821
  • (2)移位的角度:
    1. 因为2 ^ 32-1的二进制表达是:11111111 11111111 11111111 11111111
    2. 所以2 ^ 32-9的二进制表达可以写为:11111111 11111111 11111111 11111111-00000000 00000000 00000000 00001000=11111111 11111111 11111111 11110111
    3. 现对其右移两位:00111111 11111111 11111111 11111101,然后将其以十进制的形式输出即可。

验证一下输出:

#include<stdio.h>int main(void)
{int b = 0b00111111111111111111111111111101;printf("%d", b);return 0;
}

执行结果如下:
在这里插入图片描述
执行结果正确,证明上述解法可行。


4️⃣ 右移负数位:

✨昨天我们了解了左移负数位的情况,发现那是未定义的行为,现在我们来看看右移负数位又会如何?let's go!!!
在这里插入图片描述
我们先来看一段代码:

#include<stdio.h>int main(void)
{int a = 9;printf("%d\n", a >>  0);printf("%d\n", a >> -1);printf("%d\n", a >> -2);printf("%d\n", a >> -3);return 0;
}

执行结果如下:
在这里插入图片描述

💔咦❓这个输出有点意思,到底是怎么回事呢❓右移负数位竟然没有报错,那就是合理的❓既然合理,那为啥会出现这种结果呢❓按照我们以往的思维,右移-1位就是左移1位啊❗️结果不应该是18吗,怎么不对呢❓阁下莫急,我们接着往下看:

#include<stdio.h>int main(void)
{int a = 9;printf("%d\n", a >>  0);printf("%d\n", a >> -1);printf("%d\n", a >> -2);printf("%d\n", a >> -3);printf("***\n");printf("%d\n", a >> -30);printf("%d\n", a >> -31);printf("%d\n", a >> -32);printf("%d\n", a >> -33);printf("%d\n", a >> -34);printf("%d\n", a >> -35);return 0;
}

执行效果如下:
在这里插入图片描述
💔咦?下面这个结果也有点出乎意料啊!9>>-30结果是2❗️9>>-32结果是9❗️相信如果你对数字比较敏感的话,应该已经发现了右移负数位的规律。当然,如果没有发现也不用着急,我们继续往下看:

#include<stdio.h>int main(void)
{int a = 9;printf("%d\n", a >>  0);printf("%d\n", a >> -1);printf("%d\n", a >> -2);printf("%d\n", a >> -3);printf("***\n");printf("%d\n", a >> -30);printf("%d\n", a >> -31);printf("%d\n", a >> -32);printf("%d\n", a >> -33);printf("%d\n", a >> -34);printf("%d\n", a >> -35);printf("***\n");printf("%d\n", a >> -62);printf("%d\n", a >> -63);printf("%d\n", a >> -64);printf("%d\n", a >> -65);printf("%d\n", a >> -66);printf("%d\n", a >> -67);return 0;
}

在这里插入图片描述
❤️通过第三个代码我们可以看出:
🌟右移-32位的倍数的时候和右移0位时类似,都是其本身;
🌟右移-30位和右移-62位类似,都是2,那2又有什么特殊之处呢?我们来看看它们的补码:

  • 9的原(补)码是:00000000 00000000 00000000 00001001
  • 2的原(补)码是:00000000 00000000 00000000 00000010

可以看出,9>>2 = 2,且32-(abs(-30)%32)=232- (abs(-62)%32)=2

🌟右移-31位和右移-63位类似,都是4

  • 4的原(补)码是:00000000 00000000 00000000 00000100

我们知道9>>1 = 4,且32-(abs(-31)%32)=132- (abs(-63)%32)=1

所以,经过上述的推导我们可以得出右移负数位的计算公式:
若记右移n位(n为负数),并记结果为result,则
result=32-(abs(n)%32)

(此为博主自己总结的结论,如有错误还请指正,如需引用还请注明出处)

当然,右移负数位在平常很少用到(一般都在一定范围内左移或右移,别自己给自己找麻烦)。


二、拓展应用:

✨下面的第k位均为从右往左第k位(从第0位开始数),如果习惯按第1位开始,则可令k=k+1;

1. 去除低k位:

给定一个数x,将其低k位去除后再输出。
方法:直接右移k位即可,x>>k

2. 取第k位的值:

二进制表达只有0或1,所以第k位要么是0,要么是1。
方法:将x右移k位后 和1位于 or 和0位或
(x>>k)&1 or (x>>k)|0

  • 除此之外,还有其他的一些操作,都可以通过位运算的相关定义得出,此处不再赘述!

三、写在后面的话:

🔥自从chatgpt等大语言模型出现之后,立刻就有了相当广泛的应用。不论是商用还是民用,像是平常询问零碎的知识点,聊天,写代码等等,都有了其一席之地。不可否认,它们的确很强大。但随着其进一步发展,就拿CSDN平台来说,无论是问答还是写博客,都或多或少地存在着它们的影子。

🔥先说写博客方面,过分依赖于gpt写的博客和人写的博客其实差异还是蛮大的,因为前者写的大都比较生硬,基本以大片大片的概念为主,缺乏和观者的互动;并且其所述的知识也不一定都是正确的,所以我想说什么,你懂的。

🔥再说问答方面,我无法忍受一个外行人完全借助gpt来回答各行各业的问题,你回答对了我不说什么,但你完全借其所答,拿着错误的答案去回复别人,这既是一种对问者的不尊敬,也是对自己行为的不负责。我认为,它应该成为一种提升自己能力的工具,而不是将其信奉为教条,它可以用来验证我们的想法,也可以帮我们打开思路,但唯独不能代替我们。
在这里插入图片描述

在这里插入图片描述
在这里插入图片描述


好了,今天的讲解就到这里了,相信你也是收获满满吧!接下来我将会开专栏讲解数据结构和算法Python等相关知识,希望对你能有所帮助!


在这里插入图片描述

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.rhkb.cn/news/109043.html

如若内容造成侵权/违法违规/事实不符,请联系长河编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

Linux用户与组管理(02)(七)

提示&#xff1a;文章写完后&#xff0c;目录可以自动生成&#xff0c;如何生成可参考右边的帮助文档 目录 前言 一、批量创建 二、修改属性 三、密码设置 四、删除 总结 前言 今天学习的是上次剩余的用户组的内容&#xff0c;也是相对于刚学习Linux系统比较重要的部分&#x…

13.4 目标检测锚框标注 非极大值抑制

锚框的形状计算公式 假设原图的高为H,宽为W 锚框形状详细公式推导 以每个像素为中心生成不同形状的锚框 # s是缩放比&#xff0c;ratio是宽高比 def multibox_prior(data, sizes, ratios):"""生成以每个像素为中心具有不同形状的锚框"""in_he…

一文搞懂深度信念网络!DBN概念介绍与Pytorch实战

目录 一、概述1.1 深度信念网络的概述1.2 深度信念网络与其他深度学习模型的比较结构层次学习方式训练和优化应用领域 1.3 应用领域图像识别与处理自然语言处理推荐系统语音识别无监督学习与异常检测药物发现与生物信息学 二、结构2.1 受限玻尔兹曼机&#xff08;RBM&#xff0…

LLMs训练的算力优化Computational challenges of training LLMs

当您尝试训练大型语言模型时&#xff0c;您仍然经常遇到的最常见问题之一是内存不足。如果您曾尝试在Nvidia GPU上训练或甚至只是加载模型&#xff0c;那么这个错误消息可能看起来很熟悉。 CUDA&#xff0c;即Compute Unified Device Architecture的缩写&#xff0c;是为Nvid…

【rust/egui】(六)看看template的app.rs:TextEdit

说在前面 rust新手&#xff0c;egui没啥找到啥教程&#xff0c;这里自己记录下学习过程环境&#xff1a;windows11 22H2rust版本&#xff1a;rustc 1.71.1egui版本&#xff1a;0.22.0eframe版本&#xff1a;0.22.0上一篇&#xff1a;这里 TextEdit 文本编辑框 其定义为&#…

Grounded Language-Image Pre-training论文笔记

Title&#xff1a;Grounded Language-Image Pre-training Code 文章目录 1. 背景2. 方法&#xff08;1&#xff09;Unified Formulation传统目标检测grounding目标检测 &#xff08;2&#xff09;Language-Aware Deep Fusion&#xff08;3&#xff09;Pre-training with Scala…

【golang】派生数据类型---指针 标识符、关键字等

1、指针 对比C/C中的指针&#xff0c;go语言中的指针显得极为简洁&#xff0c;只是简单的获取某个空间的地址 或者 根据指针变量中的内容 获取对应存储空间的内容等操作。 具体示例如下&#xff1a; go中使用指针需要注意的点&#xff1a; 可以通过指针改变它所指向的内存空…

【CSS】轮播图案例开发 ( 基本设置 | 子绝父相 | 浏览器水平居中 | 圆角设置 | 绝对定位居中设置 )

代码示例 : <!DOCTYPE html> <html lang"en"> <head><meta charset"UTF-8"><title>Banner 轮播</title><style>/* 取消浏览器或者其它标签的默认的内外边距 */* {margin: 0;padding: 0;}/* 取消列表样式 主要是…

数据采集:selenium 获取某网站CDN 商家排名信息

写在前面 工作中遇到&#xff0c;简单整理理解不足小伙伴帮忙指正 对每个人而言&#xff0c;真正的职责只有一个&#xff1a;找到自我。然后在心中坚守其一生&#xff0c;全心全意&#xff0c;永不停息。所有其它的路都是不完整的&#xff0c;是人的逃避方式&#xff0c;是对大…

【内网穿透】搭建我的世界Java版服务器,公网远程联机

目录 前言 1. 搭建我的世界服务器 1.1 服务器安装java环境 1.2 配置服务端 2. 测试局域网联机 3. 公网远程联机 3.1 安装cpolar内网穿透 3.1.1 windows系统 3.1.2 linux系统&#xff08;支持一键自动安装脚本&#xff09; 3.2 创建隧道映射内网端口 3.3 测试公网远程…

【电源专题】18650圆柱电芯内部结构及器件

18650圆柱锂离子电池是一种直径为18mm、高度为65mm的锂离子电池,它最大的特点是拥有非常高的能量密度,它是比较成熟的锂离子电池,各方面系统质量稳定性较好,广泛适用于10千瓦时左右的电池容量场合,例如在、在手机、笔记本电脑等小型电器上。 常见的18650电池分为锂离子电池…

亚马逊云科技 re:Inforce 大会云安全合规与技术实践及 Security Jam 大赛,快来报名吧!...

‍‍ 2023年8月31日在北京 亚马逊云科技 re:Inforce 大会 首次登陆中国&#xff01; 我们期待您的莅临&#xff0c; 并与您一起迎接 AI 时代&#xff0c; 开启全面智能的安全旅程&#xff01; 在13:00-17:00的 培训与动手实验环节中 云安全合规与技术实践 及 Security Jam 大赛…

Python3 列表

Python3 列表 序列是 Python 中最基本的数据结构。 序列中的每个值都有对应的位置值&#xff0c;称之为索引&#xff0c;第一个索引是 0&#xff0c;第二个索引是 1&#xff0c;依此类推。 Python 有 6 个序列的内置类型&#xff0c;但最常见的是列表和元组。 列表都可以进…

韶音骨传导耳机值得入手吗,韶音骨传导耳机可以水洗吗

韶音家的代表作可以说是OpenRun Pro骨传导耳机&#xff0c;在发声单元位置上采用了开孔的处理&#xff0c;佩戴上耳的时候发声单元可以贴合耳道&#xff0c;在低频延伸性&#xff0c;但在中高频的时候整体会出现震感&#xff0c;纤细的耳挂在佩戴的时候是有着不错的舒适度的&am…

农村农产品信息展示网站的设计与实现(论文+源码)_kaic

摘 要 随着软件技术的迅速发展,农产品信息展示的平台越来越多,传统的农产品显示方法将被计算机图形技术取代。这种网站技术主要把农产品的描述、农产品价格、农产品图片等内容&#xff0c;通过计算机网络的开发技术&#xff0c;在互联网上进行展示&#xff0c;然后通过计算机网…

单片机TVS/ESD二极管防护

TVS 瞬态电压抑制二极管Transient Voltage Suppressor ESD 静电释放二极管 Electro-Static discharge 这两种本质上都是二极管。都是利用了二极管正向导通、反向截止的特性。二极管在反向截止截止条件下&#xff0c;如果电压继续增大&#xff0c;将会引发雪崩&#xff0c;使得…

ubuntu20.04安装gcc5.4 g++5.4

在进行ubuntu20.04的系统中安装gcc g5.4中&#xff0c;会出现安装问题 1、pip安装&#xff0c;失败 2、使用apt-get install 进行安装时&#xff0c;提示没有候选项&#xff1b; 原因&#xff1a;ubuntu20.04的系统下&#xff0c;系统默认安装的gcc9.0的版本&#xff0c;默认…

7.Oracle视图创建与使用

1、视图的创建与使用 在所有进行的SQL语句之中&#xff0c;查询是最复杂的操作&#xff0c;而且查询还和具体的开发要求有关&#xff0c;那么在开发过程之中&#xff0c;程序员完成的并不是是和数据库的所有内容&#xff0c;而更多的是应该考虑到程序的设计结构。可以没有一个项…

WordPress使用子主题插件 Child Theme Wizard,即使主题升级也能够保留以前主题样式

修改WordPress网站样式&#xff0c;主题升级会导致自己定义设置的网站样式丢失&#xff0c;还需要重新设置&#xff0c;很繁琐工作量大&#xff0c;发现在WordPress 中有Child Theme Wizard子主题插件&#xff0c;使用Child Theme Wizard子主题插件&#xff0c;即使主题升级&am…

HTML-常见标签、HTML5新特性

HTML 软件架构 1.C/S架构 (1) C/S架构即Client/Server&#xff08;客户机/服务器&#xff09;结构。 (2) C/S 架构特点 ​ C/S结构在技术上很成熟&#xff0c;它的主要特点是交互性强、具有安全的存取模式、网络通信量低、响应速度快、利于处理大量数据。但是该结构的程序是…