- UTF-8 เข้ารหัสจุด Unicode ในขนาด 1–4 ไบต์ เข้ากันได้กับ ASCII และใช้ได้กับทุกภาษา
- การซิงโครไนซ์และการตรวจสอบตนเอง: รูปแบบ 0/110/1110/11110 ป้องกันการทับซ้อนและทำให้ตรวจจับข้อผิดพลาดได้ง่ายขึ้น
- เว็บและระบบ: เมตาชาร์เซ็ต การสนับสนุนจำนวนมาก และการแปลงที่ง่ายดายบน Windows/macOS/Linux
หากคุณอ่านบทความนี้ในวันนี้แล้วไม่เห็นสัญลักษณ์แปลกๆ เลย แสดงว่าเป็นเพราะ UTF-8การเข้ารหัสนี้ช่วยให้สามารถแสดงตัวอักษร เครื่องหมายกำกับเสียง สัญลักษณ์ทางเทคนิค และแม้แต่อิโมจิได้อย่างเท่าเทียมกันในเบราว์เซอร์ ระบบปฏิบัติการ หรือไคลเอนต์อีเมลสมัยใหม่ เป็นมาตรฐานที่แพร่หลายที่สุดบนเว็บ และพื้นฐานของการสื่อสารดิจิทัลตามที่เรารู้จัก
เมื่ออุปกรณ์แสดงข้อความ จริงๆ แล้วอุปกรณ์กำลังประมวลผลตัวเลข. ตัวเลขเหล่านี้คือจุดรหัสที่กำหนดโดย มาตรฐานยูนิโค้ด และแปลงเป็นไบต์ที่เดินทางผ่านเครือข่ายหรือบันทึกไว้ในไฟล์ เราทำการเปลี่ยนแปลง: UTF-8ในบรรทัดต่อไปนี้ คุณจะเข้าใจว่ามันคืออะไร มันทำงานอย่างไร เหตุใดจึงสร้างขึ้น มีข้อดีและข้อจำกัดอะไรบ้าง และจะหลีกเลี่ยงข้อผิดพลาดทั่วไปได้อย่างไร
UTF-8 คืออะไร?
UTF-8 (8-bit Unicode Transformation Format) เป็นวิธีการแปลงจุดโค้ด Unicode ให้เป็นลำดับไบต์. คุณสมบัติหลักคือการใช้ ความยาวแปรผัน:อักขระบางตัวใช้พื้นที่ 1 ไบต์ ในขณะที่อักขระบางตัวใช้พื้นที่ 2, 3 หรือ 4 ไบต์ ซึ่งหมายความว่า ข้อความที่มีอักษรละตินง่ายๆ จะกระชับแต่สามารถแสดงอักขระใดๆ ในกลุ่ม Unicode ได้เช่นกัน
มันเข้ากันได้อย่างสมบูรณ์กับ ASCII:อักขระ 128 ตัวแรก (U+0000 ถึง U+007F) จะถูกเข้ารหัสเป็นไบต์เดียวเหมือนกับ ASCII 7 บิต สิ่งนี้ช่วยให้การเปลี่ยนผ่านจากระบบเก่าเป็นไปได้สะดวกยิ่งขึ้น และอธิบายถึงความสำเร็จส่วนใหญ่ในอินเทอร์เน็ต อีเมล และโปรโตคอล IETF
UTF-8 โดดเด่นในเรื่องความแข็งแกร่ง: รวมบิตการซิงโครไนซ์ที่ช่วยให้สามารถระบุจุดเริ่มต้นของสัญลักษณ์แต่ละตัวได้อย่างน่าเชื่อถือ คุณสมบัติการซิงโครไนซ์ด้วยตนเองนี้ทำให้ ง่ายต่อการตรวจจับว่าลำดับ "ดู" เหมือน UTF-8 หรือไม่สิ่งที่มีประโยชน์มากในเครื่องมือและตัวแยกวิเคราะห์
ยูนิโค้ด: รากฐานของทุกสิ่ง
Unicode เป็นมาตรฐานสากลที่กำหนดหมายเลขเฉพาะให้กับอักขระแต่ละตัวไม่ว่าจะเป็นภาษา แพลตฟอร์ม หรือแอปพลิเคชันใดก็ตาม หมายเลขดังกล่าวเรียกว่า จุดรหัส และโดยปกติจะเขียนเป็นเลขฐานสิบหกในรูปแบบ U+XXXX (หรือตัวเลขเพิ่มเติมหากจำเป็น)
เช่น อักษรตัวใหญ่ “A” คือ U+0041ใน HTML เราสามารถเรียกมันว่า A. คอมพิวเตอร์ของคุณไม่ได้ "คิด" ว่า A เป็นตัวอักษร แต่เป็นตัวเลข 65จากนั้นการเข้ารหัส (เช่น UTF-8) จะตัดสินใจว่าจะแสดงตัวเลขนั้นเป็นไบต์อย่างไร
หากคุณต้องการตรวจสอบว่า Unicode ถูกแปลเป็นอักขระบนพีซีของคุณอย่างไรใน Windows คุณสามารถกดปุ่ม Alt ค้างไว้แล้วพิมพ์รหัสตัวเลขทศนิยมบนแป้นตัวเลข ตัวอย่างเช่น Alt+65 คืนค่า “A” (ดู รายชื่อรหัส Alt ทั้งหมด) เป็นทางลัดแบบคลาสสิกที่แสดงให้เห็นว่ารหัสอยู่ภายใต้ตัวอักษรที่คุณเห็นอย่างไร
ประวัติย่อ: UTF-8 ถือกำเนิดขึ้นได้อย่างไร
UTF-8 ได้รับการคิดค้นโดย Ken Thompson โดยอิงตามเกณฑ์ของ Rob Pike เมื่อวันที่ 2 กันยายน พ.ศ. 1992. ทั้งสองนำไปประยุกต์ใช้งานในระบบปฏิบัติการ แผน 9 จาก Bell Labs และนำเสนออย่างเป็นทางการใน USENIX (ซานดิเอโก มกราคม 1993). ในช่วงมาตรฐานได้รับการสนับสนุนโดย กลุ่มความร่วมมือระหว่างประเทศแบบเปิด X/Open (XOJIG), ได้รับชื่อเช่น FSS/UTF และ UTF-2 จนกระทั่งมีการจัดตั้งเป็น UTF-8
การออกแบบช่วยแก้ไขปัญหาในทางปฏิบัติ ความพยายามก่อนหน้านี้ในการเข้ารหัสสากลมีดังนี้: ความเข้ากันได้กับ ASCII การซิงโครไนซ์ด้วยตนเอง การไม่มีการทับซ้อนระหว่างไบต์ และความง่ายในการตรวจจับข้อผิดพลาด ความสมดุลนี้ทำให้มันกลายเป็นมาตรฐานโดยพฤตินัยของเว็บ.
UTF-8 ทำงานอย่างไรภายใต้ประทุน
UTF-8 จัดกลุ่มอักขระตามไบต์ที่จำเป็นในการเข้ารหัสจำนวนไบต์ขึ้นอยู่กับจุดโค้ด Unicode โดยเฉพาะและปฏิบัติตามรูปแบบบิตที่ระบุความยาวของลำดับ
- 1 ไบต์ (U+0000 ถึง U+007F): อักขระ ASCII รูปแบบ:
0xxxxxxxบิตที่สำคัญที่สุดคือ 0 ซึ่ง รับประกันความเข้ากันได้โดยตรงกับ ASCII. - 2 ไบต์ (U+0080 ถึง U+07FF): รูปแบบ
110yyyyy 10xxxxxx. ใช้สำหรับตัวอักษรยุโรปส่วนใหญ่ที่มีเครื่องหมายกำกับเสียงและตัวอักษรอื่นๆ เช่น กรีก ซีริลลิก ฮีบรู หรืออาหรับ. - 3 ไบต์ (U+0800 ถึง U+FFFF): รูปแบบ
1110zzzz 10yyyyyy 10xxxxxx. รวมถึงแผนพื้นฐานหลายภาษา (BMP) พร้อม CJK (จีน ญี่ปุ่น เกาหลี)สัญลักษณ์ทางเทคนิคและอักขระที่ใช้กันทั่วไป - 4 ไบต์ (U+10000 ถึง U+10FFFF): รูปแบบ
11110uuu 10uuzzzz 10yyyyyy 10xxxxxx. แสดงถึงระนาบเสริม: สัญลักษณ์ทางคณิตศาสตร์ขั้นสูง งานเขียนทางประวัติศาสตร์ สัญลักษณ์อุดมคติที่ไม่ค่อยพบเห็นบ่อย ฯลฯ
กุญแจสำคัญในการซิงโครไนซ์ตัวเองอยู่ที่บิตส่วนหัว: 0 สำหรับ ASCII; 110 สำหรับสองไบต์; 1110 สำหรับสามไบต์; 11110 สำหรับสี่ไบต์ ไบต์ต่อเนื่อง พวกเขามักจะเริ่มต้นด้วยเลข 10. ขอบคุณที่ ไบต์ต่อเนื่องไม่สามารถปรากฏเป็นไบต์เริ่มต้นได้และลำดับที่ถูกต้องไม่สามารถเป็นสตริงย่อยของลำดับที่ยาวกว่าได้ (หลักการไม่ทับซ้อนกัน)
ความเทียบเท่ากับ UTF-16 และคู่ตัวแทน
UTF-16 แสดงถึงจุดรหัส BMP ที่มีหน่วย 16 บิต และจุดเหนือ U+FFFF ด้วย คู่ทดแทน อยู่ในช่วง D800–DFFF. แทน, UTF-8 เข้ารหัสจุดรหัสจริงเสมอไม่ใช่หน่วย UTF-16 ซึ่งหลีกเลี่ยงการสับสนกับสิ่งทดแทน
ในอดีตร่างบางฉบับอนุญาต 5 หรือ 6 ไบต์ ใน UTF-8 เพื่อครอบคลุมช่วงที่กว้างขึ้นแต่ Unicode และ RFC 3629 จำกัด UTF-8 ไว้สูงสุด 4 ไบต์ISO/IEC เคยพิจารณาทางเลือกที่กว้างขึ้น แต่ปัจจุบันไม่ได้เป็นส่วนหนึ่งของมาตรฐานอีกต่อไป
ตัวอย่างการปฏิบัติ: ñ
อักขระ “ñ” มีจุดรหัส U+00F1ซึ่งอยู่ในช่วงสองไบต์ ตามรูปแบบนี้ จะถูกเข้ารหัสเป็น 110xxxxx 10xxxxxx. การแสดง UTF-8 คือ 0xC3 0xB1การถอดรหัสเป็นกระบวนการย้อนกลับ: การอ่านส่วนที่มีประโยชน์และสร้างจุดรหัสดั้งเดิมขึ้นมาใหม่
ข้อดีและข้อจำกัดของ UTF-8
ข้อดีหลัก:
- การรองรับ ASCII:ข้อความ ASCII ถูกต้องในรูปแบบ UTF-8 โดยไม่มีการเปลี่ยนแปลง
- สากล: สามารถแสดงอักขระ Unicode ใดๆ ก็ได้ รวมถึงสัญลักษณ์ทางเทคนิคและอิโมจิ
- ประสิทธิภาพในข้อความภาษาละติน: เมื่อใช้ 1 ไบต์สำหรับ ASCII ประหยัดพื้นที่เมื่อเทียบกับ UTF-16 ในภาษาตะวันตกมากมาย
- การซิงโครไนซ์และการตรวจจับด้วยตนเอง: รูปแบบบิตอนุญาต ตรวจจับจุดเริ่มต้นของตัวละคร และตรวจสอบลำดับได้อย่างง่ายดาย
ข้อจำกัดและการแลกเปลี่ยน:
- ข้อความ CJK ใช้พื้นที่มากกว่าข้อความ UTF-16ซึ่งอักขระจำนวนมากเหล่านี้สามารถใส่ลงในไบต์คงที่ 2 ตัวได้
- ต้นทุนการคำนวณ: มีความยาวแปรผัน การดำเนินการบางอย่าง (เช่น "ไปที่อักขระ n") ต้องดำเนินการตั้งแต่ต้นและงานบางอย่างอาจเร็วกว่าในรูปแบบ UTF-16/UTF-32
BOM (Byte Order Mark) ใน UTF-8
UTF-8 ไม่จำเป็นต้องมี BOM เพราะลำดับไบต์ไม่เปลี่ยนความหมายของค่า (หน่วยที่เล็กที่สุดคือไบต์) ถึงอย่างนั้นก็ตาม มี BOM ให้เลือกอักขระ U+FEFF เข้ารหัสเป็น EF BB BF ที่จุดเริ่มต้นของไฟล์หรือสตรีม ซึ่งสามารถใช้เพื่อระบุว่า “นี่คือ Unicode/UTF-8”
แนวปฏิบัติที่ดี:หากปรากฏขึ้นตอนเริ่มต้น ระบบบางระบบจะยอมรับและบางระบบจะปฏิบัติตามอย่างเคร่งครัด ในการเชื่อมต่อกัน ขอแนะนำให้กำจัด BOM ตัวกลางออกไม่จำเป็นต้องรวมไว้และประโยชน์ของมันใน UTF-8 นั้นมีจำกัดเมื่อเทียบกับ UTF-16/UTF-32 ซึ่งทำเครื่องหมายไว้ ความอดทน.
ข้อผิดพลาดในการเขียนโค้ดทั่วไปและวิธีรับมือ
ตัวถอดรหัส UTF-8 ที่แข็งแกร่งควรปฏิเสธลำดับที่ผิดรูป หรือแทนที่ด้วย U+FFFD (อักขระแทนที่) หรือรายงานข้อผิดพลาด ข้อผิดพลาดที่พบบ่อยที่สุด ได้แก่:
- ลำดับที่ถูกตัดทอน: ไบต์นำหลายไบต์ที่ไม่มีความต่อเนื่องเพียงพอ
- ไบต์ต่อเนื่องหลวม: ปรากฏ
10xxxxxxโดยไม่มีไบต์นำที่ถูกต้อง - ความยาวเกิน: การเข้ารหัสด้วยไบต์มากกว่าที่จำเป็น เช่น การพยายามเข้ารหัส ASCII ด้วย 2 ไบต์ (
0xC0y0xC1ไม่ถูกต้อง). - ความยาวที่ห้าม: เริ่มแนะนำ 5 หรือ 6 ไบต์ (
0xF8-0xFDไม่ถูกต้อง ในมาตรฐาน UTF-8) - ค่าที่อยู่นอกช่วง Unicode: ไม่รองรับเหนือ U+10FFFF; ค่าบางอย่าง (
0xF5-0xF7เป็นจุดเริ่มต้น) ถือเป็นโมฆะ - คู่ตัวแทน UTF-16:
D800–DFFFไม่ใช่จุดรหัสที่ถูกต้อง ในรูปแบบ Unicode ไม่ควรปรากฏเป็นรหัส UTF-8
เมื่อคุณเห็นตัวอักษร “�” บนหน้าจอมีแนวโน้มสูงว่าการเข้ารหัสไม่ตรงกันหรือไฟล์ถูกบันทึกไว้ในหน้าโค้ดอื่น วิธีแก้ไขคือ บังคับใช้ UTF-8 แบบ end-to-end (ไฟล์, เซิร์ฟเวอร์, ฐานข้อมูล, ส่วนหัว HTTP)
UTF-8 บนเว็บและในอีเมล
หน้า HTML ควรประกาศการเข้ารหัสเพียงหนึ่งเดียววิธีที่แนะนำสำหรับความเข้ากันได้และการเข้าถึงคือ UTF-8 ใส่เมตาแท็กไว้ในส่วนหัวโดยเร็วที่สุด:
<meta charset="UTF-8">
วางไว้ที่จุดเริ่มต้นของ เพื่อให้เบราว์เซอร์สามารถอ่านได้ก่อนประมวลผลเอกสาร เพื่อป้องกันความไม่สอดคล้องและอักขระที่ขาดหาย การนำ UTF-8 มาใช้บนเว็บมีมากมายมหาศาล, ถูกใช้โดยเว็บไซต์ส่วนใหญ่ในปัจจุบัน
ในอีเมล์ UTF-8 ได้รับการสนับสนุนอย่างกว้างขวาง และได้รับการแนะนำโดยองค์กรต่างๆ เช่น Internet Mail Consortium กำหนดค่าไคลเอนต์อีเมลให้ใช้ UTF-8 ช่วยลดปัญหาในการแลกเปลี่ยนข้อความกับผู้คนที่ใช้ภาษาอื่น
UTF-8, UTF-16 และ UTF-32 มีความแตกต่างกันอย่างไร?
UTF-8: ความยาวตัวแปรในหน่วย 8 บิต เหมาะสำหรับเว็บไซต์มีประสิทธิภาพมากกับ ASCII และภาษาตะวันตก มีความเข้ากันได้ดีเยี่ยมและตรวจจับข้อผิดพลาดได้ดีเยี่ยม
UTF-16: ความยาวตัวแปรในหน่วย 16 บิต ใช้คู่ตัวแทนสำหรับ U+10000 ขึ้นไป โดยปกติแล้วจะเป็นประโยชน์เมื่ออักขระที่ไม่ใช่ ASCII โดดเด่นและใช้ใน API และแพลตฟอร์มต่างๆ มากมาย (เช่น Windows ทำงานแบบเนทีฟใน UTF-16).
UTF-32: ความยาวคงที่ 32 บิตต่ออักขระ ง่ายมากในการทำดัชนีแต่กินพื้นที่มาก สงวนไว้สำหรับกรณีที่ขนาดไม่สำคัญต่อความเรียบง่ายในการประมวลผล
ตัวแปรที่เข้ากันไม่ได้: CESU-8 และ “Modified UTF-8”
ซีเอสยู-8 เข้ารหัสหน่วย UTF-16 โดยตรง (รวมถึงคู่ตัวแทน) แทนที่จะเข้ารหัสจุดรหัส ซึ่งเป็นเหตุว่าทำไมมันจึงแตกต่างจากมาตรฐาน UTF-8 สำหรับอักขระที่สูงกว่า U+FFFF แพลตฟอร์มทางประวัติศาสตร์บางแห่งใช้: Oracle 8 เสนอให้ใช้ชื่อ UTF8 และเริ่มต้นด้วย Oracle 9 เพิ่มมาตรฐาน UTF-8 พร้อมด้วยนามแฝงอื่น Java และ Tcl ได้ใช้ CESU-8 ในบริบทบางอย่าง
UTF-8 ที่ปรับเปลี่ยนแล้ว (เช่นในสภาพแวดล้อม Java) แสดงอักขระ NUL (U+0000) เป็น 0xC0 0x80 แทนที่จะเป็น 0x00 หลีกเลี่ยงไบต์ว่างในสตริง C แต่มันไม่สอดคล้องกับมาตรฐาน UTF-8 การใช้งานเวอร์ชัน "ที่แก้ไข" นี้ยังมีหลายกรณี ปฏิบัติตามมาตรฐาน CESU-8.
UTF-8 บน Windows และ API: หน้าโค้ดและการแปลง
Windows ทำงานภายในในรูปแบบ UTF-16 (WCHAR)แต่ตั้งแต่ Windows 10 เวอร์ชัน 1903 คุณสามารถทำได้ บังคับให้ UTF-8 เป็นหน้าโค้ดกระบวนการ ผ่านทางแอปพลิเคชัน manifest (คุณสมบัติ activeCodePage) ซึ่งจะทำให้โค้ดเก่าที่ใช้ API “-A” ทำงานบน UTF-8 ได้ง่ายขึ้น
API -A เทียบกับ -W: -A ขึ้นอยู่กับหน้ารหัส ANSI กำหนดค่า (สามารถเป็น CP_UTF8) ในขณะที่ -W พวกเขาใช้ UTF-16. เพื่อทำงานร่วมกัน มัลติไบต์เป็นไวด์ชาร์ y ไวด์ชาร์ทูมัลติไบต์ ช่วยให้คุณสามารถแปลงระหว่าง UTF-8 และ UTF-16 ได้ สหรัฐอเมริกา CP_UTF8 และถ้ามีการใช้ MB_ERR_INVALID_CHARS เพื่อตรวจจับข้อผิดพลาดในการป้อนข้อมูล
UTF-8 รองรับโดยเบราว์เซอร์สมัยใหม่ (Chrome, Firefox, Safari, Edge, Opera และ Internet Explorer เวอร์ชันล่าสุด) และ ด้วยระบบปฏิบัติการส่วนใหญ่ (Windows, Linux, macOS, Android, iOS) ยกเว้นซอฟต์แวร์เก่ามาก คุณไม่ควรมีปัญหาใดๆ.
วิธีการแปลงไฟล์เป็น UTF-8
ใน Windows (Notepad):เปิดไฟล์ ไปที่ “ไฟล์ > บันทึกเป็น…” และภายใต้ “การเข้ารหัส” ให้เลือก UTF-8. ให้บันทึกด้วยชื่อใหม่หากคุณต้องการเก็บชื่อเดิมไว้
บน macOS (TextEdit): ใน “TextEdit > การกำหนดลักษณะ > เปิดและบันทึก” เลือก ยูนิโคด (UTF-8) เมื่อบันทึก จากนั้นส่งออกไฟล์โดยเปิดใช้งานตัวเลือกนั้น
บน Linux: ด้วยเทอร์มินัลคุณสามารถใช้ iconv. ตัวอย่างเช่น iconv -f <codificación_origen> -t UTF-8 <entrada> -o <salida>. ตรวจสอบภายหลัง ซึ่งแอพพลิเคชันที่ใช้ก็คาดหวัง UTF-8 เช่นกัน
จะทราบได้อย่างไรว่าไฟล์เป็น UTF-8 หรือไม่ ตัวแก้ไขสมัยใหม่หลายตัวจะระบุสิ่งนี้ไว้ในแถบสถานะ หากคุณเห็นอักขระแปลกๆ เช่น "�" เครื่องหมายกำกับเสียงที่ผิดเพี้ยน หรือ "ñ/ç" ที่แสดงไม่ถูกต้อง ตรวจสอบการเข้ารหัสไฟล์และการตั้งค่าตัวแก้ไข/เซิร์ฟเวอร์/DB.
แนวทางปฏิบัติที่ดีเพื่อหลีกเลี่ยงความประหลาดใจ
ประกาศ UTF-8 โดยเร็วที่สุด ในส่วนหัว HTML และ HTTP จัดเรียงโค้ดทั่วทั้งสแต็ก (ไฟล์ต้นฉบับ เทมเพลต ฐานข้อมูล และการเชื่อมต่อ) หลีกเลี่ยงการผสมการเข้ารหัส ในหน้าเดียวหรือการไหลและใช้เครื่องมือที่ตรวจสอบ/ทำให้อินพุตเป็นมาตรฐาน
สำหรับการบูรณาการและ API, ระบุการเข้ารหัสในส่วนหัวเสมอ (Content-Type: application/json; charset=UTF-8ตัวอย่างเช่น) ทดสอบด้วยข้อมูลหลายภาษา (สำเนียง CJK อิโมจิ) เพื่อค้นหาจุดอ่อนก่อนการผลิต
UTF-8 ชนะเพราะมีความสมดุลระหว่างความเข้ากันได้ ประสิทธิภาพ และการเข้าถึงถือเป็นวิธีที่ได้ผลที่สุดในการรับรองว่าข้อความจะเดินทางได้อย่างสมบูรณ์ระหว่างวัฒนธรรม ระบบ และแอปพลิเคชันต่างๆ โดยไม่คำนึงว่าจะมีสำเนียง สัญลักษณ์ทางเทคนิค หรือสคริปต์ที่ไม่ใช่ภาษาละตินหรือไม่
สารบัญ
- UTF-8 คืออะไร?
- ยูนิโค้ด: รากฐานของทุกสิ่ง
- ประวัติย่อ: UTF-8 ถือกำเนิดขึ้นได้อย่างไร
- UTF-8 ทำงานอย่างไรภายใต้ประทุน
- ข้อดีและข้อจำกัดของ UTF-8
- BOM (Byte Order Mark) ใน UTF-8
- ข้อผิดพลาดในการเขียนโค้ดทั่วไปและวิธีรับมือ
- UTF-8 บนเว็บและในอีเมล
- UTF-8, UTF-16 และ UTF-32 มีความแตกต่างกันอย่างไร?
- ตัวแปรที่เข้ากันไม่ได้: CESU-8 และ “Modified UTF-8”
- UTF-8 บน Windows และ API: หน้าโค้ดและการแปลง
- ความเข้ากันได้จริง: เบราว์เซอร์และระบบ
- วิธีการแปลงไฟล์เป็น UTF-8
- แนวทางปฏิบัติที่ดีเพื่อหลีกเลี่ยงความประหลาดใจ