鍍金池/ 教程/ C/ 練習(xí)7:更多變量和一些算術(shù)
練習(xí)9:數(shù)組和字符串
練習(xí)6:變量類型
練習(xí)3:格式化輸出
練習(xí)4:Valgrind 介紹
練習(xí)28:Makefile 進(jìn)階
練習(xí)14:編寫并使用函數(shù)
練習(xí)21:高級數(shù)據(jù)類型和控制結(jié)構(gòu)
練習(xí)20:Zed的強(qiáng)大的調(diào)試宏
練習(xí)18:函數(shù)指針
練習(xí)0:準(zhǔn)備
練習(xí)15:指針,可怕的指針
練習(xí)27:創(chuàng)造性和防御性編程
練習(xí)22:棧、作用域和全局
練習(xí)10:字符串?dāng)?shù)組和循環(huán)
練習(xí)8:大小和數(shù)組
練習(xí)16:結(jié)構(gòu)體和指向它們的指針
練習(xí)7:更多變量和一些算術(shù)
練習(xí)23:認(rèn)識(shí)達(dá)夫設(shè)備
練習(xí)12:If,Else If,Else
練習(xí)2:用Make來代替Python
練習(xí)1:啟用編譯器
練習(xí)11:While循環(huán)和布爾表達(dá)式
練習(xí)5:一個(gè)C程序的結(jié)構(gòu)
練習(xí)24:輸入輸出和文件
練習(xí)25:變參函數(shù)
練習(xí)13:Switch語句
練習(xí)19:一個(gè)簡單的對象系統(tǒng)
練習(xí)26:編寫第一個(gè)真正的程序
導(dǎo)言:C的笛卡爾之夢
練習(xí)17:堆和棧的內(nèi)存分配

練習(xí)7:更多變量和一些算術(shù)

你可以通過聲明int,floatchardouble類型的變量,來對它們做更多的事情,讓我們來熟悉它們吧。接下來我們會(huì)在各種數(shù)學(xué)表達(dá)式中使用它們,所以我會(huì)向你介紹C的基本算術(shù)操作。

int main(int argc, char *argv[])
{
    int bugs = 100;
    double bug_rate = 1.2;

    printf("You have %d bugs at the imaginary rate of %f.\n",
            bugs, bug_rate);

    long universe_of_defects = 1L * 1024L * 1024L * 1024L;
    printf("The entire universe has %ld bugs.\n",
            universe_of_defects);

    double expected_bugs = bugs * bug_rate;
    printf("You are expected to have %f bugs.\n",
            expected_bugs);

    double part_of_universe = expected_bugs / universe_of_defects;
    printf("That is only a %e portion of the universe.\n",
            part_of_universe);

    // this makes no sense, just a demo of something weird
    char nul_byte = '\0';
    int care_percentage = bugs * nul_byte;
    printf("Which means you should care %d%%.\n",
            care_percentage);

    return 0;
}

下面是這一小段無意義代碼背后發(fā)生的事情:

  ex7.c:1-4

  C程序的通常開始。

  ex7.c:5-6

  為一些偽造的bug數(shù)據(jù)聲明了一個(gè)int和一個(gè)double變量。

  ex7.c:8-9

  打印這兩個(gè)變量,沒有什么新東西。

  ex7.c:11

  使用了一個(gè)新的類型long來聲明一個(gè)大的數(shù)值,它可以儲(chǔ)存比較大的數(shù)。

  ex7.c:12-13

  使用%ld打印出這個(gè)變量,我們添加了個(gè)修飾符到%d上面。添加的"l"表示將它當(dāng)作長整形打印。

  ex7.c:15-17

  只是更多的算術(shù)運(yùn)算和打印。

  ex7.c:19-21

  編撰了一段你的bug率的描述,這里的計(jì)算非常不精確。結(jié)果非常小,所以我們要使用%e以科學(xué)記數(shù)法的形式打印它。

  ex7.c:24

  以特殊的語法'\0'聲明了一個(gè)字符。這樣創(chuàng)建了一個(gè)“空字節(jié)”字符,實(shí)際上是數(shù)字0。

  ex7.c:25

  使用這個(gè)字符乘上bug的數(shù)量,它產(chǎn)生了0,作為“有多少是你需要關(guān)心的”的結(jié)果。這條語句展示了你有時(shí)會(huì)碰到的丑陋做法。

  ex7.c:26-27

  將它打印出來,注意我使用了%%(兩個(gè)百分號(hào))來打印一個(gè)%字符。

  ex7.c:28-30

  main函數(shù)的結(jié)尾。

這一段代碼只是個(gè)練習(xí),它演示了許多算術(shù)運(yùn)算。在最后,它也展示了許多你能在C中看到,但是其它語言中沒有的技巧。對于C來說,一個(gè)“字符”同時(shí)也是一個(gè)整數(shù),雖然它很小,但的確如此。這意味著你可以對它做算術(shù)運(yùn)算,無論是好是壞,許多軟件中也是這樣做的。

在最后一部分中,你第一次見到C語言是如何直接訪問機(jī)器的。我們會(huì)在后面的章節(jié)中深入。

你會(huì)看到什么

通常,你應(yīng)該看到如下輸出:

$ make ex7
cc -Wall -g    ex7.c   -o ex7
$ ./ex7
You have 100 bugs at the imaginary rate of 1.200000.
The entire universe has 1073741824 bugs.
You are expected to have 120.000000 bugs.
That is only a 1.117587e-07 portion of the universe.
Which means you should care 0%.
$

如何使它崩潰

像之前一樣,向printf傳入錯(cuò)誤的參數(shù)來使它崩潰。對比%c,看看當(dāng)你使用%s來打印nul_byte變量時(shí)會(huì)發(fā)生什么。做完這些之后,在Valgrind下運(yùn)行它看看關(guān)于你的這次嘗試會(huì)輸出什么。

附加題

  • 把為universe_of_defects賦值的數(shù)改為不同的大小,觀察編譯器的警告。
  • 這些巨大的數(shù)字實(shí)際上打印成了什么?
  • long改為unsigned long,并試著找到對它來說太大的數(shù)字。
  • 上網(wǎng)搜索unsigned做了什么。
  • 試著自己解釋(在下個(gè)練習(xí)之前)為什么char可以和int相乘。