1. 程式人生 > >ANSI C 與 K&R C

ANSI C 與 K&R C

C語言由Dennis M.Ritchie在1973年設計和實現。從那以後使用者逐漸增加。到1978年Ritchie和Bell實驗室的另一位程式專家Kernighan合寫了著名的《TheC ProgrammingLanguage》,將C語言推向全世界,許多國家都出了譯本,國內有一些C語言書就是這本書的翻譯或者編譯。由這本書定義的C語言後來被人們稱作K&R C。
隨著C語言使用得越來越廣泛,出現了許多新問題,人們日益強烈地要求對C語言進行標準化。這個標準化的工作在美國國家標準局(ANSI)的框架中進行(1983-1988),最終結果是1988年10月頒佈的ANSI標準X3.159-1989,也就是後來人們所說的ANSIC標準。由這個標準定義的C語言被稱作ANSI C。
ANSI C標準很快被採納為國際標準和各國的標準。國際標準為ISO/IEC9899-1990,中國國家標準GB/T 15272-94是國際ISO標準的中文翻譯。
ANSIC標準化工作的一個主要目標是清除原來C語言中的不安全、不合理、不精確、不完善的東西。由此也產生了ANSIC與K&RC之間的差異。從總體上看,這些差異反應的是C語言走向完善、走向成熟。
ANSI C 對 K&R C 的修訂
(本段根據《C ProgrammingLanguage》和C語言標準整理。不求完整,希望列出最常見的差異)
 
 
1.對於原始檔內部的識別符號,有效的最小長度擴充到31個字元。檔案間連線時,識別符號的最小有效長度仍然為6個字元。(許多實現都支援更大的長度)
2.增加了幾個新關鍵字:void,const,volatile,signed,enum。拋棄了老關鍵字entry。
3.在換意字元 \ 之後寫非規定的序列,其作用確定為無定義。
4.規定8和9都不是八進位制數的合法字元。
5.引進了數的字尾字元:整數的U和L,浮點數的F和L。
6.規定連續出現的字串常量將被拼接在一起。
7.引進了“寬字元”的概念。
8.將字元也確定為帶符號(signed)和不帶符號(unsigned)的。
9.丟棄了long float(原來作為double的同義詞)。
10.引入了void型別,用 (void*)表示通用指標的型別(過去人們通常用 (char*))。
11.對算術型別規定了最小表示範圍。要求每個C語言系統用標頭檔案(<limits.h>和<float.h>)說明實現中的具體規定。
12.引進了列舉定義enum。
13.採用了來自C++的型別修飾符,如const。
14.規定字串常量是不可修改的。
15.改變了算術型別的隱含轉換規則。
16.刪去了一些過時賦值運算子,如 =+。規定賦值運算子都是基本單詞,如+= 之間不能有空格分隔。
17.引進了與一元 - 運算子對應的一元 + 運算子。
18.指向函式的指標可以直接放在函式呼叫的位置,不必顯式地寫間接操作。
19.允許結構地整體賦值,作為函式引數和返回值傳遞。
20.允許將取地址運算子作用於陣列,得到的是指向有關陣列的指標。
21.標準規定 sizeof 運算子的返回值為 size_t型別(某個無符號整型),這一型別在標準標頭檔案<stddef.h>裡定義。同時在那裡定義的還有ptrdiff_t 型別,它是指標減運算的結果型別。
22.規定取地址運算子不能作用於 register 變數。
23.規定移位表示式的型別為其左運算物件的型別。
24.允許建立指向過陣列末元素一個位置的指標,以及對它的算術運算和關係運算。
25.(從C++)引進了包含引數型別的函式原型概念,引進了變長引數表函式的概念。仍允許老的形式,但僅僅是作為過時形式保留。
26.標準規定任何區域性宣告的作用域僅僅是當前的塊(複合語句)。
27.規定函式引數作為加入函式體(複合語句)的宣告,因此不能用變數宣告去覆蓋。
28.有關名字空間的規定:所有結構、聯合和列舉標記在一個名字空間裡,標號是另一個名字空間。
29.聯合變數在定義時也可以初始化,規定初始化其第一個成分。
30.自動結構、聯合和陣列也可以初始化,但限制其初始化方式(其中只能包含常量表達式)。
31.帶大小描述的字元陣列也可以用大小與之相同的字串常量初始化(結束的\0 被刪除)。
32.開關語句的控制表示式和case標號可以是任何整型的(包括字元型別)。
 
大部分的關於C的著作都提到ANSI CStandard,但我相信少有C程式設計師真正細緻閱讀過ANSIC標準(當然了對於作C編譯器的程式設計師來說這個標準肯定是爛熟於胸了^_^),在這個系列的文章中我將和大家一起瀏覽一下ANSIC標準(C99,以下稱標準),呵呵,當然也不能面面俱到,只是“走馬觀花”。
1. 什麼是“標準”(這裡指程式語言標準)
按照comp.lang.c的CFAQ的意思:“標準只是把現存的實踐整理成文。程式語言標準可以看作語言使用者和編譯器實現者之間的協議。協議的一部分是編譯器實現者同意提供,使用者可以使用的功能。而其它部分則包括使用者同意遵守,編譯器實現者認為會被最受的規則。只要雙方都恪守自己的保證,程式就可以正確執行。如果任何一方違背它的諾言, 則結果肯定失敗。
2. ANSI C Standard到底講了啥?
這就是標準中"Scope"一節所要講述的問題。按照標準說明:標準詳細說明了使用C語言書寫的程式的形式,規範對這些程式的解釋。包括:
-- C程式的表示法;
-- C語言的語法和約束;
-- 解釋C程式的語義規則;
-- C程式輸入和輸出的表示;
-- 一份標準的實現的限定和約束。