說明:由於在各種語言中各種整型數據是會受到各種的規範(如在java的整型中byte只有分配一個字節8位,最大的long類型有8個字節也就是說最大能表示2的64次的數)那麼在java中對於超過2的64次方的整數進行運算時該怎麼辦?(通常對這個數被稱爲大數)
解法:對與一個整數來說,既然不能用一個類型來表示,那麼只能用一個整型的數組來表示來。對與即將操作的數進行分段表示。此處爲了方便表示以及能夠表達我想表達的內容,這裏用int型的數組,對一個不超過16位的數進行加、減、乘(由於乘法對於數的位數影響這裏最大支持8位)除(對於兩個大數來說個人感覺除法沒什麼用處,畢竟除法會影響精度,兩個大數相除結果一定很小。 這裏只寫了一個大數被一個小數除的除法)。
+、-、*、/
如圖:對一個16位的數進行分割,每4位一組存放在int[] A和B中將結果放在C中。
注意:由於規定每個數組元素只能存放一個4位數的整數,在進行運算時應該考慮進位和借位的問題,由於在不同運算下產生的借位或進位不同,故在每個方法裏用不同的解決方法。
加法:
addcheck():解決進位問題
public int addcheck(int a, int b) {
int flag;
if (a + b > 10000) //由於規定了是一個4位數故大於10000就是進位了
flag = 1;
else
flag = 0;
return flag;
}
這裏不是用boolean解決是因爲個人感覺返回int的話能直接用了。。。。。
add():解決方法
public void add() {
int flag = 0; //flag爲進位
for (int i = 3; i >= 0; i--) {
int d = addcheck(a[i], b[i]);
c[i] = a[i] + b[i] - d * 10000 + flag;
flag = d;
}
}
對與爲什麼不直接把進位賦給flag:flag是低位給高位的標誌,若當前已經產生了進位,那麼應該先考慮把高位給去掉,那麼就有這個d存在的必要了。
減法:
subcheck():
public int subcheck(int a, int b) {
if (a - b < 0)
return -1;
return 0;
}
sub():
public void sub() {
int flag = 0;
boolean temp = true;
//考慮到有可能b存放到數比a大先檢測如果是b大那麼將a b互換後在進行減法用temp記錄正負
for (int i = 0; i < 4; i++) {
if (a[i] != 0 && b[i] == 0) {
break;
}
if (a[i] < b[i]) {
c = a;
a = b;
b = c;
temp = false;
break;
}
}
for (int i = 3; i >= 0; i--) {
int d = subcheck(a[i], b[i]);
c[i] = (-d) * 10000 + a[i] - b[i] +flag;
flag = d;
}
System.out.print(temp ? "" : "-");
}
這裏的d是和加法一樣的考慮。
乘法:
int[] mulpre():兩個4位的整數相乘會最大會產生一個8位的數,考慮到最大能表示4位,故先寫一個方法返回一個數組,數組裏面有兩個元素:前4位和後4位。
public int[] mulpre(int a,int b){
int flag=10000; //表示現在b的位數10000是4位1000是3位
int tempa[]={0,0};
int tempb;
for(int i=1;i<5;i++){
tempb=b%10; //取得b中最後的一個數
b=b/10; //將b前3位給b
tempa[0]+=a*tempb/flag; //計算前4位
tempa[1]+=a*tempb%flag*(10000/flag); //計算後4位
flag/=10;
}
tempa[0]+=tempa[1]/10000;
tempa[1]%=10000;
return tempa;
}
for循環:求數組內兩個元素的大小的:比如 1234*5678,先拿8和1234乘取後4位爲tempa[1],剩下的是tempa[0],接下來就是7和1234乘取後3位乘10後和原來的tempa[1]相加,剩下的和tempa[0]相加,同理那5和6乘,得到一個包含有兩個4位數的數組。
mul():
public void mul(){
int flag;
int[] temp1=mulpre(a[3], b[3]);
int[] temp2=mulpre(a[2], b[2]);
int[] temp3=mulpre(a[3], b[2]);
int[] temp4=mulpre(a[2], b[3]);
c[3]=temp1[1];
c[2]=temp1[0]+temp3[1]+temp4[1];
flag=c[2]/10000;
c[2]=c[2]%10000;
c[1]=temp3[0]+temp4[0]+temp2[1]+flag;
flag=c[1]/10000;
c[1]=c[1]%10000;
c[0]=temp2[0];
}
這裏表示了兩個8位數的乘法(兩個8位數分別放在a和b的後兩個數組單位中)結果c[0]中應該是a[3]*b[3]的前4位,c[1]是a[3]*b[3]後4位 a[3]*b[4]、a[4]*b[3]的前4位之和,c[2]、c[3]都差不多,當然還要考慮進位的問題。
由於除法只要將c[i]中的數除,將餘數保存,在c[i+1]中使用就可以解決。
div():
public void div(int div){
int flag=0;
for(int i=0;i<4;i++){
a[i]+=flag*10000;
c[i]=a[i]/div;
flag=a[i]%div;
}
}
全部的代碼:
public class BigInteger {
public int[] a = new int[4];
public int[] b = new int[4];
public int[] c = new int[4];
public BigInteger(String c, String d) {
a = prepare(c);
b = prepare(d);
}
//該方法用於切割支付串數組 大數不能被表示嘛 只能用字符串表示了
public int[] prepare(String s) {
int[] a = new int[4];
int l = s.length();
for (int j = l, i = 3; j > 0 && i >= 0; j -= 4, i--) {
if (j > 3) {
String tem = s.substring(j - 4, j);
a[i] = Integer.parseInt(tem);
} else {
String tem = s.substring(0, j);
a[i] = Integer.parseInt(tem);
}
}
return a;
}
public void out() {
for (int i = 0; i < 4; i++)
if (c[i] != 0)
System.out.print(c[i]);
System.out.println();
}
public int addcheck(int a, int b) {
int flag;
if (a + b > 10000) //由於規定了是一個4位數故大於10000就是進位了
flag = 1;
else
flag = 0;
return flag;
}
public void add() {
int flag = 0; //flag爲進位
for (int i = 3; i >= 0; i--) {
int d = addcheck(a[i], b[i]);
c[i] = a[i] + b[i] - d * 10000 + flag;
flag = d;
}
out();
}
public int subcheck(int a, int b) {
if (a - b < 0)
return -1;
return 0;
}
public void sub() {
int flag = 0;
boolean temp = true;
//考慮到有可能b存放到數比a大先檢測如果是b大那麼將a b互換後在進行減法用temp記錄正負
for (int i = 0; i < 4; i++) {
if (a[i] != 0 && b[i] == 0) {
break;
}
if (a[i] < b[i]) {
c = a;
a = b;
b = c;
temp = false;
break;
}
}
for (int i = 3; i >= 0; i--) {
int d = subcheck(a[i], b[i]);
// System.out.println(a[i] + " " + b[i]);
c[i] = (-d) * 10000 + a[i] - b[i] + flag;
// System.out.println(c[i]);
flag = d;
}
System.out.print(temp ? "" : "-");
out();
}
public int[] mulpre(int a,int b){
int flag=10000;
int tempa[]={0,0};
int tempb;
for(int i=1;i<5;i++){
tempb=b%10;
// System.out.println(tempb);
b=b/10;
tempa[0]+=a*tempb/flag;
// System.out.println(tempa[0]);
tempa[1]+=a*tempb%flag*(10000/flag);
flag/=10;
}
tempa[0]+=tempa[1]/10000;
tempa[1]%=10000;
return tempa;
}
public void mul(){
int flag;
int[] temp1=mulpre(a[3], b[3]);
int[] temp2=mulpre(a[2], b[2]);
int[] temp3=mulpre(a[3], b[2]);
int[] temp4=mulpre(a[2], b[3]);
c[3]=temp1[1];
c[2]=temp1[0]+temp3[1]+temp4[1];
flag=c[2]/10000;
c[2]=c[2]%10000;
c[1]=temp3[0]+temp4[0]+temp2[1]+flag;
flag=c[1]/10000;
c[1]=c[1]%10000;
c[0]=temp2[0];
out();
}
public void div(int div){
int flag=0;
for(int i=0;i<4;i++){
a[i]+=flag*10000;
c[i]=a[i]/div;
flag=a[i]%div;
}
out();
}
public static void main(String[] args) {
BigInteger bi = new BigInteger("1076234", "92343241");
bi.add();
bi.sub();
bi.mul();
bi.div(2);
}
}
這是在這兒的第一篇,有什麼表達不清楚的可以找我哈,有什麼錯誤的也請多多包涵。