
1. 忘記關閉標籤
錯誤典型寫法:
遺漏了必要的閉合標籤,導致瀏覽器無法判斷 HTML 結構在哪裡結束。例如:
<!-- ❌ 錯誤範例:段落標籤沒有閉合 --> <p>這是一個段落 <div>下一個區塊</div>
在上面的錯誤範例中,<p> 開啟後卻沒有 </p>,接著又直接開始了一個新的 <div> 區塊。瀏覽器遇到這種情況時,通常會嘗試自動補上缺失的閉合標籤。然而,不同瀏覽器的自動校正行為可能略有差異,導致版面顯示出乎預期。例如,瀏覽器可能在看到 <div> 時就暗地裡幫你關閉了前面的 <p>。這樣一來,原本預期屬於段落的文字可能被截斷或包含範圍錯誤,造成排版混亂。
原因與影響:
HTML 是一種嚴謹的結構化標記語言,每一個開啟的標籤都應有對應的閉合標籤(某些空元素如 <br>、<img> 等除外)。忘記關閉標籤會使 DOM 結構出現預料外的巢狀,除了降低程式碼可讀性,更可能影響 CSS 選擇器的作用範圍或 JavaScript 操作 DOM 時的結果。長遠來看,未關閉的標籤會增加除錯難度,也可能在日後的維護中埋下隱患。
正確修正:
務必配對每一個開啟標籤與閉合標籤,確保 HTML 結構完整清晰。例如,上例應修正為:
<!-- ✅ 正確範例:段落標籤有正確閉合 --> <p>這是一個段落</p> <div>下一個區塊</div>
藉由明確地閉合 <p>,我們讓段落的範圍清楚劃定。良好的習慣是在撰寫時就同時輸入成對的標籤(許多代碼編輯器也提供了自動補全標籤的功能),以避免遺漏。每當新增一個標籤,都要記得檢查是否有相應的閉合標籤,讓 HTML 結構始終保持平衡。
2. 標籤巢狀錯誤
錯誤典型寫法:
標籤嵌套的順序不正確,出現「交錯」(overlap)情況。也就是說,內層標籤尚未閉合,就直接閉合了外層標籤,導致標籤結構錯亂。例如:
<!-- ❌ 錯誤範例:標籤交錯嵌套次序錯誤 --> <b>加粗文字 <i>斜體文字</b> 更多內容</i>
在上述範例中,<b>(粗體)和 <i>(斜體)的標籤順序錯亂:<b> 開啟後,又開啟了 <i>,但接著卻先關閉了 </b> 然後才關閉 </i>。這種交錯會讓瀏覽器困惑,不知道哪個標籤何時結束。瀏覽器通常會盡力糾正這類錯誤,它可能會自行閉合一些標籤以恢復合理的結構,但修復方式未必如我們所預期。
原因與影響:
根據 HTML 標準,標籤應當嚴格成對且遵循後進先出的順序(後開的先關)。可以將這種結構想像成堆疊(stack):最後開啟的標籤應最先閉合。如果順序搞亂,等於在結構中留下未封閉的「洞」。上述例子中,由於閉合順序錯誤,部分文字可能並未套用到預期的格式,或是 DOM 結構被瀏覽器強行拆成意想不到的片段,影響到 CSS 樣式或腳本操作。例如,瀏覽器可能會自動在適當位置插入 </i> 或 </b> 來修復結構,導致原本想同時加粗和斜體的文字範圍變小。
正確修正:
確保巢狀結構正確,維持標籤開啟和關閉的對稱性。上例正確的寫法為:
<!-- ✅ 正確範例:標籤按照巢狀順序正確閉合 --> <b>加粗文字 <i>斜體文字</i></b> 更多內容
在這個修正後的範例中,<b> 開啟後再開啟 <i>,隨後先關閉 </i>,再關閉 </b>,遵循了正確的先開後閉順序。如此一來,所有文字都能按照預期同時套用粗體和斜體效果。小技巧:當出現多層巢狀標籤時,可以利用縮排或良好的程式碼排版來輔助閱讀,確保看清楚每個標籤的結束位置。此外,使用 HTML 驗證工具也能迅速發現此類巢狀錯誤。
3. 區塊與行內元素誤用
錯誤典型寫法:
將 區塊級元素(block-level element)放在 行內元素(inline element)之內,違反了元素的允許內容規則。例如:
<!-- ❌ 錯誤範例:行內元素 <span> 裡直接放入區塊元素 <div> --> <span>文字前導 <div>區塊內容</div> 文字結尾</span>
在這段範例中,一個行內元素 <span> 內直接嵌入了一個區塊元素 <div>。依照 HTML 的內容模型,行內元素(如 <span>、<a>)一般只能包含純文字或其他行內元素;區塊元素(如 <div>、<p>、<h1> 等)則可以容納區塊或行內內容。但行內元素無法直接包含區塊級元素。瀏覽器解析上述錯誤 HTML 時,會試圖自動修正結構 —— 通常會在遇到 <div> 時自動閉合前面的 <span>。這意味著後半段「文字結尾」將被瀏覽器認為是在 <div> 之外的新段落,而非原本開發者意圖的同一段。
原因與影響:
區塊與行內元素的錯置會導致結構上下文錯亂。區塊元素通常以新行呈現,能包含較大型的區塊內容;行內元素則是在文字段落中穿插,不會換行。如果把區塊硬塞進行內元素的範圍裡,就好比試圖將大盒子裝進小盒子 —— 瀏覽器只好把小盒子提前關上,再把大盒子單獨放置。結果就是 HTML 結構被拆解成與原始程式碼縮排不同的 DOM:某些元素可能被瀏覽器移到外層,從而影響排版和 CSS 作用。例如,原本希望某段文字整體著色的 <span>,由於中途插入了非法的區塊元素,被迫提早關閉,後面的文字就失去了預期的樣式。
正確修正:
調整 HTML 結構,避免讓行內元素包含區塊元素。如果需要在文字中插入區塊級的內容,可以將整段結構提升為區塊級容器。例如,上例可以改寫為:
<!-- ✅ 正確範例:結構重組,避免 span 包含 div --> <p> <span>文字前導</span> </p> <div>區塊內容</div> <p> <span>文字結尾</span> </p>
在修正後的寫法中,我們將原本試圖混在一起的行內、區塊內容分開處理:用段落 <p> 或其他區塊容器來包裹文字,使區塊元素 <div> 不會跑進行內元素 <span> 的範圍內。如此一來,瀏覽器解析時就能得到預期的結構。另外,開發者也可以多利用 CSS 來調整排版,而非依賴在文字中硬插入區塊元素。例如,如果只是想突出一段文字,考慮使用行內元素配合 CSS,而不是插入額外的 <div>。
(註:HTML5 規範下某些以前不允許的巢狀情形有所放寬,但一般仍應遵循語意與結構規範。例如,不要在 <a> 裡再放 <button>,因為這兩者都是互動元素,巢狀會導致無效的 HTML。)
4. 列表與表格結構錯誤
結構化的列表和表格在 HTML 中有嚴格的父子關係要求。如果忽略這些要求,容易導致內容結構混亂,影響樣式和可存取性。以下分別說明:
列表結構誤用:
<ul> 或 <ol> 列表中,直屬子元素應該是 <li> 列表項(以及極少數例外如 <script>、<template>)。常見錯誤是直接在列表中放入非 <li> 元素,或是忘記使用 <li> 包裹項目內容。例如:
<!-- ❌ 錯誤範例:ul 列表中含有不合法的子元素 --> <ul> <li>項目一</li> <div>項目二</div> <!-- 這裡錯誤地用了 <div> 而非 <li> --> <li>項目三</li> </ul>
上述範例中,第二個項目誤用了 <div> 作為列表的直接子節點。瀏覽器在解析時,會察覺到 <ul> 內出現了不該直接存在的元素,很可能會自動地將 <div> 移出 <ul>,或在其前後插入缺失的標籤來勉強修復結構。結果,清單的編號或項目的樣式可能因此走樣;使用者在使用螢幕閱讀器等輔助技術時也可能無法正確理解清單結構。
正確的做法是確保所有列表項都置於 <li> 中,例如:
<!-- ✅ 正確範例:使用 <li> 作為列表項容器 --> <ul> <li>項目一</li> <li>項目二</li> <li>項目三</li> </ul>
若需要在單一列表項中放入更複雜的結構(例如包含段落或區塊的內容),可以在該 <li> 裡使用區塊元素進一步包裹,這在 HTML 結構上是允許的。重點在於不要跳過 <li> 這一層級。
表格結構誤用:
表格(<table>)中的結構層次也很固定:表格裡應包含表列 <tr>,而 <tr> 中才容納表格儲存格 <td> 或表頭 <th>。常見錯誤是忘記寫 <tr> 就直接塞入 <td>,或表列、儲存格標籤沒有正確對應。例如:
<!-- ❌ 錯誤範例:缺少 <tr> 將 <td> 直接放入 table --> <table> <td>資料1</td> <td>資料2</td> </table>
上述錯誤中,<td> 沒有被 <tr> 包住就直接出現在 <table> 下。瀏覽器解析時,可能會自動插入隱含的 <tr> 將這兩個 <td> 包起來,但這種修復並非萬無一失,也可能因為結構混亂導致表格呈現異常(例如,某些瀏覽器會把這樣的標記當作只有一行兩格的表格,但嚴謹的結構下應明確標示出那是一行)。
正確的表格結構寫法如下:
<!-- ✅ 正確範例:table 中正確使用 tr 包裹 td -->
<table>
<tr>
<td>資料1</td>
<td>資料2</td>
</tr>
</table>
除此之外,表格還有 <thead>、<tbody>、<tfoot> 等分區容器可以使用,以標示表格的表頭、主體和結尾區塊。即便不使用這些分區,也務必遵守 <table> → <tr> → <td> 的基本階層順序。違反這種階層規則的 HTML,除了在視覺呈現上可能出問題,更會影響資料表被輔助技術(如螢幕閱讀器)正確理解,對無障礙性造成負面影響。
5. HTML 文件結構不完整
一個完整的 HTML 文件除了頁面內容本身,還需要正確的文件宣告與基本結構。如果這些「骨架」遺漏或錯置,瀏覽器可能進入非標準模式,或導致某些預期的行為失效。
錯誤典型寫法:
缺少文件類型宣告 (<!DOCTYPE html>),或者未包含必要的 <html>、<head>、<body> 區塊。比如,有些初學者撰寫 HTML 時,直接開始寫內容卻沒有宣告:
<!-- ❌ 錯誤範例:缺少 <!DOCTYPE> 及 <html><head><body> 等結構 --> <title>我的頁面</title> <p>歡迎光臨!</p>
上述範例中,整個 HTML 文件缺少了 <!DOCTYPE html> 宣告,也沒有 <html> 根元素。甚至 <title> 標籤出現在了 <body> 外部。瀏覽器在解析時會採用許多容錯機制,例如自動加上缺失的 <html>、<head>、<body> 標籤,把 <title> 移動到正確的位置等等。但更大的問題是:如果沒有正確的 <!DOCTYPE>,瀏覽器可能會進入所謂的怪異模式(quirks mode)。在怪異模式下,瀏覽器會用向後相容的方式來解析和呈現頁面,這可能導致 CSS 盒模型計算與標準模式有所差異,使得排版和樣式變得難以預測。
原因與影響:
<!DOCTYPE html> 是告訴瀏覽器此文件使用 HTML 最新標準的宣告。缺少它時,舊版瀏覽器會假設你使用過時的 HTML 版本並切換到怪異模式;就連現代瀏覽器也保留了怪異模式以相容老舊頁面。這可能影響到 CSS 的解析(例如在標準模式下,CSS 盒模型計算元素寬度時不包含邊框 (border) 和內距 (padding),但在怪異模式下某些瀏覽器會把它們算進寬度),或讓一些新標準特性無法正常運作。另一方面,<html>、<head>、<body> 等標籤則構成了 HTML 文件的基本結構:<head> 包含頁面的元資訊(例如字符編碼宣告、<meta name="viewport">、樣式連結、腳本載入,以及前述的 <title> 等),而 <body> 則容納可見的頁面內容。如果把本該放在 <head> 的標籤寫到了 <body> 裡(或反之),那些標籤可能就不會如預期發揮作用。例如,<meta charset="UTF-8"> 若被寫在 <body> 部分,瀏覽器可能已在解析頭部時預設了錯誤的編碼,導致頁面出現亂碼。
正確修正:
撰寫完整的 HTML 骨架,並遵循元素該所在的位置。良好的起手式包括:
<!-- ✅ 正確範例:包含 <!DOCTYPE> 和基本 HTML 結構 --> <!DOCTYPE html> <html lang="zh-Hant"> <head> <meta charset="UTF-8"> <meta name="viewport" content="width=device-width, initial-scale=1.0"> <title>我的頁面</title> </head> <body> <p>歡迎光臨!</p> </body> </html>
這段範本展示了標準的文件開頭結構:先是 <!DOCTYPE html> 宣告,告知瀏覽器使用標準模式。接著 <html> 元素,並通常帶有語言屬性 lang(上述範例使用繁體中文 "zh-Hant")。<head> 部分放置字符編碼、關鍵的 meta 標籤,以及頁面標題等,確保它們在內容載入前正確配置。然後 <body> 中才是實際顯示給使用者看的內容。遵守這個結構可以避免很多潛在問題。在現代的前端開發中,即使透過框架或樣板自動生成頁面,也要確認這些基本結構沒有遺漏,以確保頁面在各種環境下都能正常運行。