CSAPPLab1-DataLab

news2025/3/1 11:55:31

1、bitXor

异或:不是同时为0和不是同时为1的情况进行按位与

/*
 * bitXor - x^y using only ~ and &
 *   Example: bitXor(4, 5) = 1
 *   Legal ops: ~ &
 *   Max ops: 14
 *   Rating: 1
 */

int bitXor(int x, int y)
{
  return ~(~x & ~y) & ~(x & y);
}

2、tmin

int最小值就是符号位为1,其他为0

/*
 * tmin - return minimum two's complement integer
 *   Legal ops: ! ~ & ^ | + << >>
 *   Max ops: 4
 *   Rating: 1
 */

int tmin(void)
{
  return 0x01 << 31;
}

3、isTmax

我们考虑四位的最大值x=0111 然后x+1之后就会变成1000,我们对1000取非0111就会重新变回x值,已知自己与自己异或会得到0,也就是说我们可以用异或来判断等于!((~(x+1)^x)) 是否为1即可判断是否为最大值。这里有一个例外就是x=-1,由于-1=1111 他利用上面的式子判断也符合,故要特判-1,利用!!(x+1) 这个操作-1和最大值并不相同

/*
 * isTmax - returns 1 if x is the maximum, two's complement number,
 *     and 0 otherwise
 *   Legal ops: ! ~ & ^ | +
 *   Max ops: 10
 *   Rating: 1
 */

int isTmax(int x)
{
  return !(~(x + 1) ^ x) & !!(x + 1);
}

4、allOddBits

A=1010, A是一个典型的奇数位都是1的数(起始位为第0位),那只要一个四位的二进制数X & A = A就说明这个二进制符合条件,即只要判断x & 0xAAAAAAAA == 0xAAAAAAAA 就可以了。

由于不能直接定义0xAAAAAAAA ,我们需要一些位运算的小技巧

/*
 * allOddBits - return 1 if all odd-numbered bits in word set to 1
 *   where bits are numbered from 0 (least significant) to 31 (most significant)
 *   Examples allOddBits(0xFFFFFFFD) = 0, allOddBits(0xAAAAAAAA) = 1
 *   Legal ops: ! ~ & ^ | + << >>
 *   Max ops: 12
 *   Rating: 2
 */

int allOddBits(int x)
{
  int mask = 0xAA;            // 0xAA
  mask = (mask << 8) + mask;  // 0xAAAA
  mask = (mask << 16) + mask; // 0xAAAAAAAA
  return !((x & mask) ^ mask);
}

5、negate

A + ~A = -1 和 A + (-A) =0 利用这两个式子我们可以得到 (-A) = ~A + 1

int值机器数为补码,补码取负为: 所有位取反然后加1即可

/*
 * negate - return -x
 *   Example: negate(1) = -1.
 *   Legal ops: ! ~ & ^ | + << >>
 *   Max ops: 5
 *   Rating: 2
 */

int negate(int x)
{
  return ~x + 1;
}

6、isAsciiDigit

我们可以看到“十”位必须是3, 并且只需要“个”位小于A即可,这里的小于运算 ,用了 a < b = a + (-b) < 0的性质,x & 0xF保存了x的后四位, 加上(-A)是否为负数来判断后四位的范围,判断负数是与0x1 << 31进行按位与运算,如果结果最高位为1则为负数

/*
 * isAsciiDigit - return 1 if 0x30 <= x <= 0x39 (ASCII codes for characters '0' to '9')
 *   Example: isAsciiDigit(0x35) = 1.
 *            isAsciiDigit(0x3a) = 0.
 *            isAsciiDigit(0x05) = 0.
 *   Legal ops: ! ~ & ^ | + << >>
 *   Max ops: 15
 *   Rating: 3
 */

int isAsciiDigit(int x)
{
  int ah = !(x >> 4 ^ 0x3);
  int al = x & 0xF;
  int minus_a = ~0xA + 1;
  int flag = 0x1 << 31;
  return ah & !!((al + minus_a) & flag);
}

7、conditional

当x非0, 则!x为0, !!x为1, 令x = !!x,则此时~x+1为全1

若x为0, 则!!x为0, ~x+1还是为0

/*
 * conditional - same as x ? y : z
 *   Example: conditional(2,4,5) = 4
 *   Legal ops: ! ~ & ^ | + << >>
 *   Max ops: 16
 *   Rating: 3
 */
// x > 0 return y else return z

int conditional(int x, int y, int z)
{
  x = !!(x);
  x = ~x + 1;
  return (x & y) | ((~x) & z);
}

8、isLessOrEqual

注意:直接用x-y可能会爆int故不能通过这样简单的判断, 故进行分类讨论

  • case 1代表x < 0, y > 0,
  • case 2代表x > 0, y < 0。
  • 在x y同号时(同大于0或同小于0时),我们可以放心的进行x-y操作,这样确保不会因为溢出而导致结果的符号错误,因此这两种情况可以合并为一种情况, 即case 3。

显然case 1是符合条件的,case 2不符合条件但它却是统一讨论情况3的障碍,所以最终在返回条件中一定要有!case 2来将情况2排除掉,再与两种同号条件相与。

/*
 * isLessOrEqual - if x <= y  then return 1, else return 0
 *   Example: isLessOrEqual(4,5) = 1.
 *   Legal ops: ! ~ & ^ | + << >>
 *   Max ops: 24
 *   Rating: 3
 */
// 若x<=y则返回1, 否则返回0

int isLessOrEqual(int x, int y)
{
  int sign_x = (x >> 31) & 0x1;
  int sign_y = (y >> 31) & 0x1;
  // case 1: x为-,y为+
  int case_1 = sign_x & (!sign_y);

  // case 2: x为+,y为-
  int case_2 = (!sign_x) & sign_y;

  // case 3: x与y同号
  int minus_y = (~y) + 1; // -y
  int sum = x + minus_y;  // x + (-y) = x - y

  // 判断sum是否 <= 0
  // 判断 = 0,若sum == 0, eq一定为1
  int eq = !sum;
  // 判断 < 0,若sum < 0,less一定为1
  int less = (sum >> 31) & 0x1;

  return case_1 | (!case_2 & (eq | less));
}

9、logicalNeg

非零数x,-x | x一定可以保证符号位为1。而对于0,这样的结论是不成立的,这就找到了能够完全区分0值和非0值的一个清晰的边界。

/*
 * logicalNeg - implement the ! operator, using all of
 *              the legal operators except !
 *   Examples: logicalNeg(3) = 0, logicalNeg(0) = 1
 *   Legal ops: ~ & ^ | + << >>
 *   Max ops: 12
 *   Rating: 4
 */

int logicalNeg(int x)
{
  int res = ((x | (~x + 1)) >> 31); // //除了0以外,其他的数都可以让res取到全1
  return res + 1;                   // res=0xffffffff, 因为int右移符号扩展 x|(~x+1)在x非0情况下必定是负数
}

10、howManyBits

        为了便于处理,将负数转换成对应的反码,再求解最高位1所在的位置

        正数的话直接求解最高位1所在的位置即可。最终结果为,最高位1所在的位置 + 1(符号位),比如,0111 -> 3 + 1(符号位)

        注:这里最高位所在的位置表示该位置是第几位(从1开始计算), 第一位、第二位、......

求解最高位1所在位置使用二分法:

        如果x的高16位不为0,将x右移16位,然后用b16记录一下最高位1后面至少有16个数,

x右移16位之后,再接着二分,右移8位,

        如果x的高8位不为0,将x右移8位,然后用b8记录一下最高位1后面至少有8个数

        以此类推,最后将最高位1后面的数(包括自己)都加起来,即b16 + b8 + b4 + b2 + b1 + b0,再加一个符号位,即为最终答案b16 + b8 + b4 + b2 + b1 + b0 + 1

/* howManyBits - return the minimum number of bits required to represent x in
 *             two's complement
 *  Examples: howManyBits(12) = 5
 *            howManyBits(298) = 10
 *            howManyBits(-5) = 4
 *            howManyBits(0)  = 1
 *            howManyBits(-1) = 1
 *            howManyBits(0x80000000) = 32
 *  Legal ops: ! ~ & ^ | + << >>
 *  Max ops: 90
 *  Rating: 4
 */

int howManyBits(int x)
{
  int b16, b8, b4, b2, b1, b0;
  int sign = x >> 31;
  x = (sign & ~x) | (~sign & x);

  b16 = !!(x >> 16) << 4; // 10000, 16
  x = x >> b16;
  b8 = !!(x >> 8) << 3; // 1000, 8
  x = x >> b8;
  b4 = !!(x >> 4) << 2; // 100, 4
  x = x >> b4;
  b2 = !!(x >> 2) << 1; // 10, 2
  x = x >> b2;
  b1 = !!(x >> 1); // 1, 1
  x = x >> b1;
  b0 = x;
  return b16 + b8 + b4 + b2 + b1 + b0 + 1;
}

浮点数部分最重要的是理解下面这张图(太重要了!!!,不然根本没思路解题)

11、floatScale2

// float
/*
 * floatScale2 - Return bit-level equivalent of expression 2*f for
 *   floating point argument f.
 *   Both the argument and result are passed as unsigned int's, but
 *   they are to be interpreted as the bit-level representation of
 *   single-precision floating point values.
 *   When argument is NaN, return argument
 *   Legal ops: Any integer/unsigned operations incl. ||, &&. also if, while
 *   Max ops: 30
 *   Rating: 4
 */
unsigned floatScale2(unsigned uf)
{
  unsigned s = (uf >> 31) & (0x1);
  unsigned exp = (uf >> 23) & (0xff);
  unsigned frac = (uf & 0x7fffff);

  // 0
  if (exp == 0 && frac == 0)
    return uf;

  // 无穷大/NAN
  if (exp == 0xff)
    return uf;

  // 非规格化
  if (exp == 0)
  {
    // E = exp - 127 = -127
    // frac
    frac <<= 1; // *2
    return (s << 31) | frac;
  }

  // 规格化
  exp++; // E = exp - 127

  return (s << 31) | (exp << 23) | (frac);
}

12、floatFloat2Int

/*
 * floatFloat2Int - Return bit-level equivalent of expression (int) f
 *   for floating point argument f.
 *   Argument is passed as unsigned int, but
 *   it is to be interpreted as the bit-level representation of a
 *   single-precision floating point value.
 *   Anything out of range (including NaN and infinity) should return
 *   0x80000000u.
 *   Legal ops: Any integer/unsigned operations incl. ||, &&. also if, while
 *   Max ops: 30
 *   Rating: 4
 */
int floatFloat2Int(unsigned uf)
{
  unsigned s = (uf >> 31) & (0x1);
  unsigned exp = (uf >> 23) & (0xff);
  unsigned frac = (uf & 0x7fffff);

  // 0
  if (exp == 0 && frac == 0)
    return 0;

  // 无限大/NAN
  if (exp == 0xff)
    return 0x80000000u;

  // 非规格化
  if (exp == 0)
  {
    // M 0.1111... < 1
    // E = 1 - 127 = -126
    return 0;
  }

  // 规格化
  // M 1.xXXXX
  int E = exp - 127;
  frac = frac | (1 << 23);

  if (E > 31) // 爆int
    return 0x80000000u;
  else if (E < 0)
  {
    return 0;
  }

  // M * 2^E
  if (E > 23)
  {
    frac <<= (E - 23);
  }
  else
  {
    frac >>= (23 - E);
  }

  if (s)
    return ~frac + 1;
  return frac;
}

13、floatPower2

/*
 * floatPower2 - Return bit-level equivalent of the expression 2.0^x
 *   (2.0 raised to the power x) for any 32-bit integer x.
 *
 *   The unsigned value that is returned should have the identical bit
 *   representation as the single-precision floating-point number 2.0^x.
 *   If the result is too small to be represented as a denorm, return
 *   0. If too large, return +INF.
 *
 *   Legal ops: Any integer/unsigned operations incl. ||, &&. Also if, while
 *   Max ops: 30
 *   Rating: 4
 */
/*
    非规格化浮点数的范围:2^-149 - 2^-126
    规格化浮点数的范围:  2^-126 - 2^127
*/
unsigned floatPower2(int x)
{
  if (x < -149)
    return 0;
  else if (x < -126)
  {
    // E = x
    // E = 1 - 127 = -126
    int shift = 23 + (x + 126);
    return 1 << shift;
  }
  else if (x <= 127)
  {
    // x = exp - bias
    int exp = x + 127;
    return exp << 23;
  }
  else
  {
    return (0xff) << 23;
  }
}

测试结果 


写在最后:笔者仰慕CSAAPLab已久,今日终于可以动手做做了,不得不说,Lab的质量确实高,做完本次实验,感觉自己对计算机中信息位的表示与处理的理解更深了一步,由于写博客的时间比较仓促,博客中出现的问题还请各位大神在评论区批评指正,谢谢大家!

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

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

可鉴别加密工作模式-同时保护数据机密性和完整性(OCB、CCM、KeyWrap、EAX和GCM)第一部分

当算法用于同时保护数据的机密性和完整性时&#xff0c;应选取合适的可鉴别加密工作模式&#xff0c;例如OCB、CCM、KeyWrap、EAX和GCM等工作模式。以下总结来自GBT36624-2018国标文本。 在可鉴别加密工作模式之前&#xff0c;先来说说分组密码的工作模式可参考GBT17964-2021版…

反欺诈(羊毛盾)API 实现用户行为分析的思路分析

简介 反欺诈&#xff08;羊毛盾&#xff09;API 是一种用于识别和防范各种欺诈行为的技术解决方案。它可集成到各种应用程序和平台中&#xff0c;通过手机号码、手机IP进行异常检测&#xff0c;达到防范恶意注册、虚假评论、虚假交易等欺诈行为的目的。 本文主要介绍反欺诈&a…

1677_MIT 6.828 xv6中增加CPU alarm

全部学习汇总&#xff1a; GreyZhang/g_unix: some basic learning about unix operating system. (github.com) 前面把课程要求做了一个简单的翻译&#xff0c;从课程的要求说明中其实已经能够得到很多的提示。这个alarm的功能&#xff0c;其实有点类似回调函数的概念&#xf…

基于springboot+mysql+jsp实现校园新闻发布系统

基于springbootmysqljsp实现校园新闻发布系统 一、系统介绍1、系统主要功能&#xff1a;2.涉及技术框架&#xff1a;3.本项目所用环境&#xff1a; 二、功能展示三、其它系统四、获取源码 一、系统介绍 1、系统主要功能&#xff1a; 普通用户&#xff1a;浏览主页面&#xff…

【音视频处理】直播工作原理,直播CDN、推流拉流、流媒体服务究竟是什么

大家好&#xff0c;欢迎来到停止重构的频道。 本期我们讨论直播技术。 我们将会介绍&#xff0c;直播工作原理&#xff0c;流媒体服务的作用&#xff0c;推流/拉流、直播CDN等等。 这里需要特别说明的是&#xff0c;直播指的是&#xff1a;1对多的直播&#xff0c;平常直播平…

基于copula的风光联合场景生成与缩减

目录 1 主要内容 风光出力场景生成方法 2 部分程序 3 程序结果 4 程序链接 点击直达&#xff01; 1 主要内容 该程序方法复现《融合风光出力场景生成的多能互补微网系统优化配置》风光出力场景生成部分&#xff0c;目前大多数研究的是不计风光出力之间的相关性影响&…

grpc 使用demo示例

一、 编写proto文件 1、idea新建java项目&#xff0c;在maven中引入以下依赖&#xff1a; <dependencies><!--grpc底层通信组件--><dependency><groupId>io.grpc</groupId><artifactId>grpc-netty-shaded</artifactId><version&g…

Java笔记_10(项目阶段----拼图游戏)

项目阶段 页面搭建创建窗口 界面设置和菜单搭建创建菜单 添加图片图片对象 打乱图片用一维数组添加值到二维数组中 事件美化页面移动图片查看完整图片&#xff0c;作弊器&#xff0c;判断胜利计步器和菜单业务的实现弹窗创建 更换图片和登陆页面的建立表单 所有源码的实现游戏规…

es7.x集群部署-多台物理机部署-docker环境部署-docker-compose管理

es集群部署文档 部署es服务的三台服务器的ip和host分分别是&#xff1a; iphost_name192.168.1.2web02192.168.1.3storage02192.168.1.4Storage03 这个配置需要在服务器上编写对应的hosts文件&#xff0c;然后才可以使用host进行配置。 本次部署没有外挂配置文件&#xff0…

容器内无tcpdump,如何在宿主机上抓容器的包

抓包的容器里&#xff0c;没有安装tcpdump 命令&#xff0c;我们可以去容器所在宿主机上&#xff0c;使用 nsenter 命令切换网络命名空间后&#xff0c;使用宿主机上的tcpdump 命令&#xff0c;对容器进行抓包分析。 此例中&#xff0c;我要抓取容器中端口是5240的包&#xff…

react3:受控组件(表单默认变成受控)-组件通信 - typescript项目(表单,tabbar)

受控组件&#xff1a;表单 非受控组件表单元素值不受所在组件状态的控制, 我们将这样的表单元素称作: 非受控组件. 受控组件受控组件 : 值受到 React 组件状态控制的表单元素一般是通过 defaultValue 属性, onChange 事件配合将非受控组件变为受控组件. 多表单元素操作 &#…

Unity中GPUInstance详解

为什么要用GPUInstance 在没有GPUInstance此技术之前&#xff0c;对于像草地、树木&#xff0c;割草游戏&#xff0c;它们往往是数据量很大&#xff0c;但同时又只存在微小的差别如位置、旋转、颜色等。如果像常规物体那样进行渲染&#xff0c;所使用的绘制指令必然很多…

3.3 向量与矩阵的范数

学习目标&#xff1a; 要学习向量与矩阵的范数&#xff0c;我会采取以下几个步骤&#xff1a; 了解基本概念&#xff1a;首先&#xff0c;我会了解向量和矩阵的范数的基本概念和定义&#xff0c;以及它们的性质和特点&#xff0c;这是理解和掌握范数的基础。 学习具体算法&am…

Nacos简介、基本概念、基本架构、安装部署

官网&#xff1a;https://nacos.io/zh-cn/ 官方文档&#xff1a; 什么是 Nacos Github&#xff1a;https://github.com/alibaba/nacos&#xff0c;阿里巴巴开源项目。 简介 什么是Nacos&#xff1f; Nacos&#xff1a;(Dynamic) Naming and Configuration Service&#xf…

空间相关性----地理探测器--学习记录

目录 相关教程--软件及数据准备 R语言数据分析1、R包、数据准备、GD综合代码2、分异及因子探测---q值 gd3、交互作用探测---评估因子gdinteract4、风险区探测--显著性--gdrisk()5、生态探测---交叉影响--gdeco() 数据准备注意&#xff1a;使用Arcgis首先创建.gdb&#xff08;本…

数学建模第二天:数学建模工具课之MATLAB绘图操作

目录 一、前言 二、二维绘图 1、曲线图、散点图plot 2、隐函数、显函数与参数方程的绘图 ①ezplot ②fplot 三、三维绘图 1、单曲线plot3 2、多曲线plot3 3、曲面 ①实曲面surf ②网格曲面mesh 四、特殊的二维、三维图 1、极坐标图polar 2、平面散点图scatter …

学网络安全都是一群什么人?

大家好呀&#xff0c;我是知了姐&#xff0c;又是一期学员故事栏目~ 3月下旬知了堂信安方向开新班&#xff0c;知了姐跟着去采访&#xff0c;了解到新学员们的求学故事&#xff0c;嘿你别说&#xff0c;虽然大家出身专业不同、经历背景不同&#xff0c;如今却在同一个地点相遇…

CAMX大气臭氧来源解析模拟

查看原文>>>基于CAMX大气臭氧来源解析模拟与臭氧成因分析实践技术应用 随着我国经济快速发展&#xff0c;我国面临着日益严重的大气污染问题。大气污染是工农业生产、生活、交通、城市化等方面人为活动的综合结果&#xff0c;同时气象因素是控制大气污染的关键自然因…

【微信小程序】生命周期,插槽和组件间通信

一、组件的生命周期 1.1 组件全部的生命周期函数 小程序组件可用的全部生命周期如下表所示 生命周期函数参数描述说明created无在组件实例刚刚被创建时执行attached无在组件实例进入页面节点树时执行ready无在组件在视图层布局完成后执行moved无在组件实例被移动到节点树另一…

实战案例|聚焦攻击面管理,腾讯安全威胁情报守护头部券商资产安全

金融“活水”润泽千行百业&#xff0c;对金融客户来说&#xff0c;由于业务场景存在特殊性和复杂性&#xff0c;网络安全必然是一场“持久战”。如何在事前做好安全部署&#xff0c;构建威胁情报分析的防护体系至为重要&#xff0c;实现更为精准、高效的动态防御。 客户名片 …