跳至內容

英文维基 | 中文维基 | 日文维基 | 草榴社区

代碼風格

本頁使用了標題或全文手工轉換
維基百科,自由的百科全書

代碼風格(英語:Programming style)即程序開發人員所編寫源代碼的書寫風格。良好的代碼風格會幫助程序員閱讀和理解符合該風格的源代碼,並且避免錯誤。

關於該主題的經典著作是 1970 年代編寫的《編程風格的要素》英語The Elements of Programming Style,並以當時流行的 FortranPL/I 語言的示例進行了說明。

特定程序中使用的編程風格可能源自公司或其他計算組織的代碼約定英語Coding conventions,以及代碼作者的偏好。編程風格通常是為特定的編程語言(或語言家族)設計的:在 C 源代碼中被認為是良好的風格可能不適合 BASIC 源代碼等等。但是,一些規則通常適用於許多語言。

良好風格的要素

[編輯]

總結程序設計實踐中的經驗,代碼風格的要素包括(但不限於)以下幾點:

代碼外觀

[編輯]

代碼風格通常處理源代碼的可視外觀,帶有可讀性的目標。軟件很長時間都可以格式化源代碼,讓寫代碼的人將注意力集中在命名,邏輯和更高級的技術。作為一個實際的點,用計算機來格式化源代碼節省了時間,且使不帶網絡論戰地實施全公司的標準成為可能。

縮進

[編輯]

縮進風格協助確認控制流和代碼塊。在一些編程語言中,縮進被用來限定代碼的邏輯塊;在這些情況下正確的縮進不僅僅是風格的事。在其他語言中,縮進和空白字符不影響功能,雖然有邏輯和一貫的縮進是代碼更易於閱讀。比較:

if (hours < 24 && minutes < 60 && seconds < 60) {
    return true;
} else {
    return false;
}

if (hours < 24 && minutes < 60 && seconds < 60)
{
    return true;
}
else
{
    return false;
}

和像是這樣

if  ( hours   < 24
   && minutes < 60
   && seconds < 60
)
{return    true
;}         else
{return   false
;}

前兩個示例很可能更容易閱讀,因為它們以既定的方式縮進("hanging paragraph" 樣式)。這種縮進風格在處理多個嵌套結構時特別有用。

ModuLiq

[編輯]

ModuLiq Zero 縮進風格用回車分組而不是縮進。和所有以上的比較:

if (hours < 24 && minutes < 60 && seconds < 60)
return true;

else
return false;

Lua

[編輯]

Lua不用傳統的花括號括號。if/else 語句只需要表達式後面有then,以end結束 if/else 語句。

if hours < 24 and minutes < 60 and seconds < 60 then
  return true
else
  return false
end

縮進是可選的。and,or,not在 true/false 語句間被使用。

它們是真/假陳述,如

print(not true)

會代表假。

Python

[編輯]

Python 用縮進來表明控制結構,所以正確的縮進是需要的。通過這麼做,用花括號(亦即{})包括的需要就被清除。另一方面,複製和粘貼 Python 代碼可能導致問題,因為被粘貼的代碼的縮進級別可能和當前行的縮進級別不同。這樣的重格式化用手做可能十分乏味,但一些文本編輯器集成開發環境有自動做的功能。也有當 Python 代碼被發表在去除空白字符的論壇或網頁上,使它變得無法使用的問題,雖然這個問題可以在能用保留空白字符的標籤,像"<pre> ... </pre>"(HTML中),"[code]"..."[/code]"(bbcode英語bbcode中)等等時避免。

if hours < 24 and minutes < 60 and seconds < 60:
    return True
else:
    return False

注意 Python 不適用花括號,而是一個普通的英文冒號(例子else:)。

許多 Python 程序員傾向於遵循一種公認的風格指南,稱為 PEP8。[1]有一些工具旨在自動化 PEP8 合規性。

Haskell

[編輯]

Haskell 類似地有越位規則,也就是它有一種二維語法,在其中縮進對定義塊有意義(雖然另一種語法用花括號和分號)。Haskell 是一種聲明式語言,在 Haskell 腳本中有語句,但是有聲明。示例:

let c_1 = 1
    c_2 = 2
in
    f x y = c_1 * x + c_2 * y

可以被寫成一行,如:

let {c_1=1;c_2=2} in f x y = c_1 * x + c_2 * y

Haskell 鼓勵 文學編程 的使用,擴展的文本解釋代碼的緣由。在文學式 Haskell 腳本(帶有擴展名lhs)中,所有東西都是注釋,除了標記為代碼的塊。程序可以用 LaTeX 編寫,這種情況下 code 環境標記哪裡是代碼。並且每個活動的代碼段落可以被在前面和後面帶上空行的方式標記,以一個大於號和一個空格開始每一行代碼。這裡有一個使用 LaTeX 標記的:

The function \verb+isValidDate+ test if date is valid
\begin{code}
isValidDate :: Date -> Bool
isValidDate date = hh>=0  && mm>=0 && ss>=0
                 && hh<24 && mm<60 && ss<60
 where (hh,mm,ss) = fromDate date
\end{code}
observe that in this case the overloaded function is \verb+fromDate :: Date -> (Int,Int,Int)+.

一個使用純文本的例子:

The function isValidDate test if date is valid

> isValidDate :: Date -> Bool
> isValidDate date = hh>=0  && mm>=0 && ss>=0
>                  && hh<24 && mm<60 && ss<60
>  where (hh,mm,ss) = fromDate date

observe that in this case the overloaded function is fromDate :: Date -> (Int,Int,Int).

垂直對齊

[編輯]

將相似的元素垂直對齊經常是有幫助的,使錯字導致的錯誤更加明顯。比較:

$search = array('a', 'b', 'c', 'd', 'e');
$replacement = array('foo', 'bar', 'baz', 'quux');

// Another example:

$value = 0;
$anothervalue = 1;
$yetanothervalue = 2;

$search      = array('a',   'b',   'c',   'd',   'e');
$replacement = array('foo', 'bar', 'baz', 'quux');

// Another example:

$value           = 0;
$anothervalue    = 1;
$yetanothervalue = 2;

空格

[編輯]

在一些需要空白字符的情況下,絕大部分自由形式語言的語法不關心出現了多少空白字符。與空白字符相關的風格被普遍用來加強可讀性。目前沒有已知的確鑿事實(研究得出的結論)關於哪種空白字符風格有最好的可讀性。

例如,比較下列語法上等價的 C 語言代碼例子:

int i;
for(i=0;i<10;++i){
    printf("%d",i*i+i);
}

v.s.

int i;
for (i = 0; i < 10; ++i) {
    printf("%d", i * i + i);
}

制表符

[編輯]

使用製表鍵來創建空白字符,在不施加足夠關注時會造成特定的問題,因為依據使用的工具,甚至是用戶的偏好,制表點的位置可能不同。 如一個例子,一個程序員偏好4個制表位英語Tab Stops,將工具集設置成如此,然後用這些去格式化代碼。

int     ix;     // Index to scan array
long    sum;    // Accumulator for sum

另一個程序員偏好8個制表位,並將工具集設置成如此。當其他人檢查原來那個人的代碼時,他們可能會發現很難讀。

int             ix;             // Index to scan array
long    sum;    // Accumulator for sum

一種對這個問題廣泛使用的解決方法可能包含不為對齊使用製表鍵,或制定必須設置成幾個制表位的規則。注意制表符在一貫的情況下工作良好,限制在局部縮進上,並且不用來對齊:

class MyClass {
	int foobar(
		int qux, // first parameter
		int quux); // second parameter
	int foobar2(
		int qux, // first parameter
		int quux, // second parameter
		int quuux); // third parameter
};

參見

[編輯]
  1. ^ PEP 0008 -- Style Guide for Python Code. python.org. [2022-08-02]. (原始內容存檔於2018-07-13).