29
大大

C 語言中的變數型態

  • Upload
    goro

  • View
    48

  • Download
    0

Embed Size (px)

DESCRIPTION

大數. C 語言中的變數型態. 資料來源: 2008 寒訓講義. 若要存 ” 擁有超過 19 位有效位數的 ” 數字?. “ 使用 array” 的概念. 把一個 n 位數的數字當作(分解成)好幾個 k 位數。 運算過程的 overflow---- 估計位數 arr[0] 要放最低位數 or 最高位數 ? arr[0] 放最高位數時,若有進位,現有位數都要往後移一格(也可預先留)。運算時,要先知道開始運算的位數(最低位)放在哪一格。要全部後移時,可用 memmove(&a[0],&b[0],sizeofbytes) 。. Input 不超過 100 位數 - PowerPoint PPT Presentation

Citation preview

Page 1: C 語言中的變數型態

大數

Page 2: C 語言中的變數型態

C 語言中的變數型態型態名稱 所需記憶體 數值範圍

bool 1 bit 0,1 (即 true 跟 false)

char 1 byte -128 ~ 127 (ASCII Code)

int 4 byte -231~231-1 (約 10 位整數 )-2,147,483,648~2,147,483,647

unsigned int 4 byte 0~232-1 (約 10 位整數 )0~4,294,967,295

long 4 byte -231~231-1 (約 10 位整數 )-2,147,483,648~2,147,483,647

unsigned long 4 byte 0~232-1 (約 10 位整數 )0~4,294,967,295

long long 8 byte -263~263-1 (約 19 位整數 )-9,223,372,036,854,775,808~9,223,372,036,854,775,807

float 4 byte ±3.4×10-38 ~ ±3.4×1038 ( 有效位數 7位 )

double 8 byte ±1.7×10-308 ~ ±1.7×10308 ( 有效位數 15位 )

long double 8 byte ±1.7×10-308 ~ ±1.7×10308 ( 有效位數 15位 )

資料來源: 2008 寒訓講義

Page 3: C 語言中的變數型態

• 若要存”擁有超過 19 位有效位數的”數字?

Page 4: C 語言中的變數型態

“使用 array” 的概念 把一個 n 位數的數字當作(分解成)好幾個 k 位數。

運算過程的 overflow---- 估計位數 arr[0] 要放最低位數 or 最高位數 ? arr[0] 放最高位數時,若有進位,現有位數

都要往後移一格(也可預先留)。運算時,要先知道開始運算的位數(最低位)放在哪一格。要全部後移時,可用memmove(&a[0],&b[0],sizeofbytes) 。

Page 5: C 語言中的變數型態

Input 不超過 100 位數567890123456789012345678995678901234567890123456789Output101357802469135780246913578

Page 6: C 語言中的變數型態

char array

1. inputASCII 轉換成整數型態

2. 開始運算3. 整數轉換成 ASCII 型態4. output

codetemp424.c

Page 7: C 語言中的變數型態

Input與 ASCII整數

資料型態 char : ASCII 的世界也是整數的世界

%d 0 … 10 48 49 … 57 65 66 … 90 97 98 …122

%c ‘\0’ … ‘\n’ ‘0’ ‘1’… ‘9’ ‘a’ ‘b’… ‘z’ ‘A’ ‘B’…’Z’

平常處理 char我們都用%c,也是看到我們熟悉的字元,但實際儲存在 char裡的資料卻是用整數的字元 ASCII碼。

上面兩組 code都會印出 10 空白 與換行。

char temp=’\n’;

printf(“%d %c”,temp,temp);

上面的 code當然也是一樣。

所以 code裡的-‘0’ -48是做甚麼用的?

‘0’ (48) >> 0

‘1’ (49) >> 1

… …

‘9’ (57) >> 9

正解:把 char裡的儲存的 整數 ASCII碼 變成 整數。

臨時忘記可以用 printf("%d %d %d %d %d %d %d %d",'\0','\n','0','9','a','z','A','Z');

char temp;

temp=10;

printf(“%d %c”,temp,temp);

int ten=10;

char temp;

temp=ten;

printf(%d %c“,temp,temp);

下一頁

Page 8: C 語言中的變數型態

stdlib.h的 int atoi(const char *nptr)

int number;char nptr[]={‘3’,’4’,’5’,’6’,’\0’}; // nptr[]=“3456”number=atoi(nptr); number=3456;

#include<stdlib.h>

Page 9: C 語言中的變數型態

直式加法• sum0=(carry0+a0+b0)mod n• carry1= (carry0+a0+b0) / n

• 一格存 1 位數的話, n 就是 10 ,因為是 10進位。

• 一格存 3 位數的話, n 就是 1000 ,因為是1000 進位。

Page 10: C 語言中的變數型態

一格存一位數arr1[4] arr1[3] arr1[2] arr1[1] arr1[0]

4 5

arr2[4] arr2[3] arr2[2] arr2[1] arr2[0]

5 6

arr3[4] arr3[3] arr3[2] arr3[1] arr3[0]

11

carry

1

11001

Page 11: C 語言中的變數型態

Input3 2

967

34

Output1001

codetemp10013.c

Page 12: C 語言中的變數型態

char array

• 跟組合語言格式一樣• +-*/與 = 都跟整數一樣• 可用字串處理函式 ch8、 9( c ), ch26( c+

+ )• strlen (以’ \0’ 標記結束位置 )(‘\0’== 整數 0)• strcpy(arr1,arr1) (會出錯)、 memmove• printf(“%s”,arr); (arr[0] 放最高位 )• 讀入字串 gets(arr)、 scanf(“%s”,arr)

Page 13: C 語言中的變數型態

直式減法c0=a0-b0-carry0if(c0<0){

c0=c0+ncarry1=1

}else{

carry1=0}

1 0 0 5

9 9 9

-100-100

-1

那 999-1005?

1 0 0 5

9 9 9

0 0 0 6

答案是 -6另外宣告 char arr3sign=‘-’;

arr2[]

arr1[]

arr3[]

-46

-1-1

0

Page 14: C 語言中的變數型態

if(a0>=b0+carry0){c0=a0-b0-carry0carry1=0;

}else{

c0=n+a0-b0-carry0carry1=1

}

c0=a0-b0-carry0if(c0<0){

c0=c0+ncarry1=1

}else{

carry1=0}

因為程設課本說有些硬體不允許在 char 裡面存負數

Page 15: C 語言中的變數型態

負數出現現在把加減法都考慮負數:大 >0 ,小 >0, |大 |>|小 |+ 大 – (+小 ) = ++ 大 – (-小 ) = +- 大 – (+小 ) = -- 大 – (-小 ) = -+ 小 – (+大 ) = -+ 小 – (-大 ) = +- 小 – (+大 ) = -- 小 – (-大 ) = +

減法就有 8 種可能性 !

Page 16: C 語言中的變數型態

• 先看加法(把加法的程式擴充)數字部分用加法,再補正負號。

else

數字部分用減法,再補正負號。

arr2-arr1 ,補正負號(與大數同號)。

正 +正負 +負正 + 負負 + 正

+ 大 +(-小 )

- 大 + (+小 )+小 +(-

大 )

-小 + (+大 )

Page 17: C 語言中的變數型態

• 再看減法(把減法的程式擴充或利用 a+(-b) 附屬在加法)

數字部分用加法,再補正負號。else

數字部分用減法,再補正負號。

arr2-arr1 ,補正負號(與大數同號)。

負 - 正正 - 負

正 - 正負 - 負

+ 大 -(+小 )

- 大 - (-小 )+ 小 -(+

大 )

- 小 - (-大 )

Page 18: C 語言中的變數型態

出現負數與減法後該注意的不論加減法,運算完後會因為連續退位出現很多 leading 0 ,至少在 output 之前要記得調整長度。

調整長度時 長度是 1 。0 0 0 0

Page 19: C 語言中的變數型態

乘法• product00=(a00*b00+carry00)mod n• carry01= (a00*b00+carry00) / n

• sum0=product00• sum1=product01+product11

125* 25-------------------------- 625 250+)------------------------ 3125

Page 20: C 語言中的變數型態

乘法arr1[4] arr1[3] arr1[2] arr1[1] arr1[0]

9 9 9

arr2[4] arr2[3] arr2[2] arr2[1] arr2[0]

9 9

arr3[4] arr3[3] arr3[2] arr3[1] arr3[0]

81

carry

8

189

999* 99-------------------------- 8991 8991+)------------------------ 98901

98998

arr3[4] arr3[3] arr3[2] arr3[1] arr3[0]

8190

9

081909819089 19998

在這個模擬中,加法被隱含在乘法中

product11+product01product12+carry12 +product02

arr3len++;

Page 21: C 語言中的變數型態

乘法被乘數有 a 位數乘數有 b 位數積最多有 a+b 位數(有人有問題嗎?):1 考慮運算過程的 overflow ,能存 n 位數的資料

型態,我們最多只存 n/2 位數2 準備好足夠的格子才放得下積做幾次加法是由乘數的格數決定

將加法包成函式現在就能再利用了特殊情況!:只要乘數為零,積為零且長度為 1 。

Page 22: C 語言中的變數型態

結構• arr[]*3 存數字:被乘數、乘數、積• position*3 存最高位位置(低位已知,可不

存)• carry 暫存進位

Page 23: C 語言中的變數型態

一格存 K 位數

Page 24: C 語言中的變數型態

一格存 K 位數arr1[4] arr1[3] arr1[2] arr1[1] arr1[0]

2 45

arr2[4] arr2[3] arr2[2] arr2[1] arr2[0]

7 56

arr3[4] arr3[3] arr3[2] arr3[1] arr3[0]

101

carry

1

110

11245

+ 756-------------------------- 1001

Page 25: C 語言中的變數型態

乘法arr1[4] arr1[3] arr1[2] arr1[1] arr1[0]

99 99 99

arr2[4] arr2[3] arr2[2] arr2[1] arr2[0]

99 99

arr3[4] arr3[3] arr3[2] arr3[1] arr3[0]

9801

carry

98

19899

999999* 9999-------------------------- 98999901 98999901+)------------------------ 9998990001

9998999998

arr3[4] arr3[3] arr3[2] arr3[1] arr3[0]

98019900

99

09801990099980199009899 199999998

在這個模擬中,加法被隱含在乘法中

product11+product01product12+carry12 +product02

arr3len++;

Page 26: C 語言中的變數型態

一格存 K 位數 以一格存 4 位數為例: printf(“%04d”,arr[i]); cout << cout.width(4) << fill(‘0’) << arr[i]; 最高位數是不用補零的 !

通常讀入數字時需要轉換(讀入格式通常不會K 位數剛好一格給你讀入),轉換可以用stdlib.h的 int atoi(const char *nptr) ,

ex: char nptr[]=“3456” -> int number=3456

Page 27: C 語言中的變數型態

I/O

• 從最高位數輸出• 最高位數不補零(一格存 K 位數)• 零仍然要顯示一個‘ 0’( 當然不補零 )

• 順應題目給的讀入格式讀入,再轉換成自己想用的儲存方式。

Page 28: C 語言中的變數型態

? sprintf (輸出數字仍要以格為單位需用迴圈)、 sscanf 並不能

用到 %s 的特性

依題目需求(空間限制、時間限制、要做乘法與否),會有不同的適用方法,若限制寬鬆,也可選擇比較容易(比較習慣)寫出 code 的方法。

ex 要節省空間時,一格存 K 位數的整數 array比 char array 好。 ex:char (1 byte) 加法可存 2 位;乘法存 1 位。 int (4bytes) 加法存 9 位沒問題;乘法存 4位 。 long long int (8bytes) 加法存 18 位沒問題;乘法存 9 位。 但是讀入數字時需要轉換,耗費轉換時間。

Page 29: C 語言中的變數型態

• 424 integer inquiry• 10013 super long sum//output 最後要換行• 10106 product• 485 pascal’s triangle of death• 495 fibonacci freeze