正在学习计算机组织与结构,为了写一些底层的算术操作模拟,比如一个二进制补码数的加减乘除,发现这很麻烦,因为不管是什么语言,都只提供了8位、32、64位等部分位数的补码形式,那么怎么实现任意任意位的补码整数呢,由于我们不能利用现有的如Byte、Integer类,所以我们需要一个容器来存储我们自己编写的任意位的补码整数。
数组可以实现,但是数组移位可能比较麻烦,比如如果要实现二进制数的算术右移,必须要移动大部分元素。可以使用链表,虽然获取二进制数某一位的值比较麻烦,但是还是比数组可能更好一点。于是,我们采用基于链表的队列。
2 3 /** 4 * Created by XuTao on 2018/12/1 15:26 5 * 作用:存储一个n位二进制数,并实现左右移动,取反等操作(补码形式) 6 */ 7 public class BinaryQueue { 8 private int size; 9 private Node head = new Node(-1); //head只是一个头节点,后面才是二进制数,从左到右,从高位到低位的 10 public BinaryQueue(int size){ //创建一个size大小的二进制,他被初始化为00...00 11 this.size = size; 12 Node temp =head; 13 for (int i =0;i<size;i++){ 14 temp .next = new Node(0); 15 temp = temp.next; 16 } 17 } 18 public BinaryQueue(String binary){ //以二进制数创建 19 this.size = binary.length(); 20 Node temp =head; 21 for (int i =0;i<size;i++){ 22 temp .next = new Node(binary.charAt(i)-‘0‘); 23 temp = temp.next; 24 } 25 } 26 public void shiftLeft(){ //左移 27 head.next = head.next.next; 28 Node temp = head.next; 29 for (int i=0;i<size;i++){ 30 if (i==size-2) { 31 temp.next = new Node(0); 32 break; 33 } 34 temp = temp.next; 35 } 36 } 37 public void shiftRight(){//右移 38 Node first = head.next; 39 head.next = new Node(0); 40 head.next.next=first; 41 42 Node temp = head; 43 for (int i =0;i<size;i++){ 44 temp = temp.next; 45 } 46 temp.next =null; 47 } 48 public void shiftRightArithmetically(){ //算术右移,符号扩展 49 Node first = head.next; 50 head.next = new Node(first.value); 51 head.next.next=first; 52 53 Node temp = head; 54 for (int i =0;i<size;i++){ 55 temp = temp.next; 56 } 57 temp.next =null; 58 } 59 60 public void reverse(){ 61 Node temp = head.next; 62 for (int i =0;i<size;i++){ 63 temp.value = 1-temp.value; //取反,是1,1-1=0;是0:1-0=1 64 temp = temp.next; 65 } 66 } 67 68 public BinaryQueue add(BinaryQueue bq){ 69 //将两个队列中的二进制放入数组中,如果长度不同则需要将短的进行算术扩展, 70 int len = bq.size>size?bq.size:size; 71 int [] arr_bq = new int[len]; 72 int [] arr_this = new int[len]; 73 if (bq.size>size){//bq 长,this扩展 74 String s = bq.getStr(); 75 for (int i =0;i<len;i++){ 76 arr_bq[i] = s.charAt(i)-‘0‘; 77 } 78 String s_this = getStr(); 79 for (int j =0 ;j<len;j++){ 80 if (j<len-size){ 81 arr_this[j] = head.next.value; 82 } 83 else { 84 arr_this[j]= s_this.charAt(j-(len-size))-‘0‘; 85 } 86 } 87 } 88 else { //this 长 ,bq扩展 89 String s = this.getStr(); 90 for (int i =0;i<len;i++){ 91 arr_this[i] = s.charAt(i)-‘0‘; 92 } 93 String s_bq = bq.getStr(); 94 for (int j =0 ;j<len;j++){ 95 if (j<len-size){ 96 arr_bq[j] = bq.head.next.value; 97 } 98 else { 99 arr_bq[j]= s_bq.charAt(j-(len-size))-‘0‘; 100 } 101 } 102 } 103 104 //相加 105 int []res = new int[len]; 106 int carry = 0; //上一次加的进位 107 for (int i = len-1;i>=0;i--){ 108 res[i] = arr_bq[i]+arr_this[i]+carry; 109 if (res[i]==2){//进位1,本位0 110 res[i]=0; 111 carry =1; 112 } 113 else if (res[i]==3){//进位1,本位1 114 res[i]=1; 115 carry =1; 116 } 117 else carry = 0; 118 } 119 String str = ""; 120 for (int i =0;i<len;i++){ 121 str+=res[i]; 122 } 123 return new BinaryQueue(str); 124 } 125 126 public BinaryQueue getOppositeNumber(){//取相反数,就是取反加一 127 String s = ""; 128 for (int i=0;i<size-1;i++){ 129 s+="0"; 130 } 131 s+="1"; 132 reverse();//取反 133 return add(new BinaryQueue(s));//加一 134 } 135 136 public int getInt(){ //获取二进制所代表的补码整数 137 if (head.next.value==1){ 138 return -Integer.valueOf(getOppositeNumber().getStr(),2); 139 } 140 return Integer.valueOf(getStr(),2); 141 } 142 143 144 public String getStr(){//获取二进制的字符串形式 145 String str =""; 146 Node temp = head.next; 147 while (temp!=null){ 148 str+=temp.value; 149 temp =temp.next; 150 } 151 return str; 152 } 153 154 public static void main(String[] args) { 155 BinaryQueue bq = new BinaryQueue("1100000011"); 156 BinaryQueue bq2 = new BinaryQueue("0000000000"); 157 // System.out.println(bq.add(bq2).getStr()); 158 // System.out.println(bq2.getOppositeNumber().getStr()); 159 System.out.println(bq.getInt()); 160 System.out.println(bq2.getInt()); 161 } 162 163 //节点类 164 class Node{ 165 int value; 166 Node next; 167 Node (int value){ 168 this.value = value; 169 } 170 } 171 } 有了我们自己定义的任意N位二进制补码数后,我们就可能进行一些其他的操作了,比如布思算法、整数除法等。
原文地址:https://www.cnblogs.com/XT-xutao/p/10050518.html
时间: 2024-10-19 21:22:32