- GNU
awk จะวนผ่าน stdin และไฟล์โดยอัตโนมัติ และจัดการงานข้อความบน CLI ได้ด้วยการประกอบคำสั่งบรรทัดเดียวสำหรับ การกรอง·การแทนที่·การจัดการฟิลด์
/regexp/ และ !/regexp/ เป็นไวยากรณ์แบบย่อสำหรับตรวจสอบบรรทัดอินพุตปัจจุบัน และถ้าเงื่อนไขเป็นจริงจะมีการ พิมพ์ $0 ออกมาโดยปริยาย
sub จะแทนที่เฉพาะรายการที่ตรงกันตัวแรก ส่วน gsub จะแทนที่ทุกรายการที่ตรงกัน และถ้าละอาร์กิวเมนต์เป้าหมายไว้ จะใช้การแทนที่กับ บรรทัดอินพุตปัจจุบัน $0
- ด้วยการแยกฟิลด์ตามช่องว่างและการใช้
$N, NF, $NF ทำให้ awk เหมาะกับงาน แบบอิงฟิลด์ เช่น การเลือกคอลัมน์เฉพาะหรือการประมวลผลตามเงื่อนไข
- เมื่อเขียนชิ้นส่วน
cond{action} ต่อกันและเพิ่ม BEGIN{}·END{} ก็สามารถสร้างโปรแกรมขนาดเล็กที่ไปไกลกว่าตัวกรองแบบง่าย ๆ และครอบคลุมทั้งสตริง ตัวเลข และ associative array ได้
วิธีการทำงานของ awk
awk สามารถกรองข้อความได้เหมือน grep, sed และยังมีความสามารถเชิงโปรแกรมสำหรับงานที่ซับซ้อนกว่านั้นด้วย
- อินพุตสามารถรับจาก stdin หรือไฟล์ได้ และโดยปกติจะวนประมวลผลทีละบรรทัดพร้อมใช้เงื่อนไขและคำสั่งที่กำหนด
- สามารถเข้าถึงทั้งบรรทัดอินพุตได้ผ่านตัวแปรพิเศษ
$0
- คำที่ถูกต้องจริง ๆ คือ input record แต่ในบทนี้จะอธิบายแบบทีละบรรทัด
การกรองและการพิมพ์ค่าเริ่มต้น
- regular expression เขียนในรูป
/.../ และเมื่อจะตรวจสอบว่าสตริงตรงกับ regex หรือไม่ จะใช้ไวยากรณ์ string ~ /regexp/
- เงื่อนไขตรงข้ามเขียนเป็น
string !~ /regexp/
- ถ้าละสตริงที่จะตรวจสอบไว้ จะถือว่าใช้
$0
- ถ้ามีแต่เงื่อนไขและไม่มีคำสั่ง เมื่อเงื่อนไขเป็นจริงจะพิมพ์
$0 ออกมาโดยอัตโนมัติ
awk '/regexp/' เป็นรูปย่อของ awk '$0 ~ /regexp/{print $0}'
awk '!/regexp/' เป็นรูปย่อของ awk '$0 !~ /regexp/{print $0}'
- ในตัวอย่างจะแสดงการพิมพ์เฉพาะบรรทัดที่มี
at หรือพิมพ์เฉพาะบรรทัดที่ไม่มี e เพื่อให้เห็นลำดับการทำงานพื้นฐานของการกรอง
สำนวนการพิมพ์ด้วย 1
- ใน conditional expression ตัวเลขที่ไม่ใช่ 0 และ สตริงที่ไม่ว่าง จะถูกประเมินว่าเป็นจริง
awk '1' เป็นสำนวนที่ใช้กำหนดเงื่อนไขซึ่งเป็นจริงเสมอสำหรับทุกบรรทัดอินพุต
- เมื่อไม่มีคำสั่ง เงื่อนไขที่เป็นจริงจะนำไปสู่การพิมพ์
$0 ดังนั้น awk '1' จึงพิมพ์อินพุตทั้งหมดออกมาตามเดิม
- ผลลัพธ์เหมือนกับ
awk '{print $0}' หรือ cat แบบตรง ๆ
การแทนที่: sub และ gsub
awk มีฟังก์ชัน sub และ gsub สำหรับค้นหาและแทนที่
sub(/:/, "-") จะแทนที่เฉพาะ : ตัวแรกในแต่ละบรรทัดอินพุตด้วย -
gsub(/:/, "-") จะแทนที่ : ทุกตัวในแต่ละบรรทัดอินพุตด้วย -
- ทั้งสองฟังก์ชันรับ regular expression ที่จะจับคู่เป็นอาร์กิวเมนต์ตัวแรก และรับสตริงสำหรับแทนที่เป็นอาร์กิวเมนต์ตัวที่สอง
- ถ้าไม่ได้ส่งสตริงอินพุตแยกต่างหากมา เป้าหมายเริ่มต้นคือ
$0
- เมื่อแทนที่สำเร็จ อินพุตเป้าหมายจะถูกแก้ไข
1 หลังบล็อกแทนที่จะถูกตีความเป็น conditional expression ที่อยู่นอกบล็อก จึงทำให้มีการพิมพ์ $0 ที่ถูกแก้ไขแล้วออกมาอีกครั้ง
awk '{sub(/:/, "-")} 1' ให้ผลเหมือน awk '{sub(/:/, "-"); print $0}'
- ต่อให้ใช้แค่
print เป้าหมายเริ่มต้นที่จะพิมพ์ก็ยังเป็น $0
เกณฑ์ในการเลือก grep, sed, awk
- สำหรับการกรองบรรทัดแบบง่าย
grep ที่ออกแบบมาเฉพาะทางอาจเร็วกว่า sed หรือ awk
- งานแทนที่ข้อความ
sed อาจเร็วกว่า awk
- ความสามารถของเครื่องมือเหล่านี้ไม่ได้จับคู่กันแบบ 1:1 เสมอไป
- หากจะทำ
grep -o ด้วย sed หรือ awk มักต้องใช้หลายขั้นตอนมากกว่า
- การค้นหาแบบ recursive มีให้เฉพาะ
grep
- ดูการอภิปรายที่เกี่ยวข้องได้ที่ unix.stackexchange: When to use grep, sed, awk, perl, etc
การประมวลผลแบบอิงฟิลด์
awk ถูกใช้งานบ่อยมากโดยเฉพาะกับ การประมวลผลแบบอิงฟิลด์
- โดยปริยายจะแบ่งบรรทัดอินพุตตามช่องว่าง และเข้าถึงแต่ละฟิลด์ได้ด้วย
$N
$2 คือฟิลด์ที่สอง
$NF คือฟิลด์สุดท้าย
NF คือจำนวนฟิลด์ทั้งหมดของบรรทัดอินพุตปัจจุบัน
- ตัวอย่าง
table.txt แสดงการประมวลผลระดับคอลัมน์อย่างกระชับ
- พิมพ์ฟิลด์ที่สองของแต่ละบรรทัด
- พิมพ์เฉพาะบรรทัดที่ฟิลด์สุดท้ายเป็นค่าลบ
- เปลี่ยน
b เป็น B เฉพาะในฟิลด์แรก
- ไฟล์ตัวอย่างอยู่ในไดเรกทอรี example_files
โครงสร้างของคำสั่งบรรทัดเดียว
- คำสั่งบรรทัดเดียวของ
awk โดยทั่วไปมีรูปแบบดังนี้
awk 'cond1{action1} cond2{action2} ... condN{actionN}'
- ถ้าไม่มีเงื่อนไข คำสั่งจะถูกเรียกทำงานเสมอ
- ถ้าไม่มีคำสั่ง เมื่อเงื่อนไขเป็นจริงจะพิมพ์
$0
- ภายในบล็อกสามารถคั่นหลาย statement ด้วยอัฒภาค
;
- การเขียนหลายบล็อกต่อกันช่วยให้คำสั่งบรรทัดเดียวส่วนใหญ่แสดงการทำงานตามเงื่อนไขได้โดยไม่ต้องใช้
if อย่างชัดเจน
awk '$NF<0' table.txt จะพิมพ์เฉพาะบรรทัดที่ฟิลด์สุดท้ายเป็นค่าลบ
BEGIN{} จะทำงานก่อนเริ่มอ่านอินพุต
END{} จะทำงานหลังประมวลผลอินพุตทั้งหมดเสร็จแล้ว
- รายละเอียดเพิ่มเติมของโอเปอเรเตอร์และ conditional expression อยู่ที่ gawk manual: Operators, gawk manual: Truth Values and Conditions
สตริงและตัวเลข
awk ตัดสินชนิดของค่าตามบริบทเพื่อให้สร้างวิธีแก้ปัญหาสั้น ๆ บน CLI ได้สะดวก
- string literal เขียนไว้ใน เครื่องหมายอัญประกาศคู่
- ตัวเลขสามารถใช้ได้ทั้งจำนวนเต็ม ทศนิยม และรูปแบบวิทยาศาสตร์
BEGIN{} ใช้ได้แม้ตอนรันโปรแกรม awk โดยไม่มีอินพุตภายนอก
- ตัวแปรสามารถเก็บได้ทั้งตัวเลขและสตริง
- ตัวอย่าง:
a=5; b=2.5; print a+b
- ถ้าวางสตริงเรียงต่อกันจะเป็นการเชื่อมสตริง
- ตัวแปรที่ยังไม่ได้กำหนดค่า จะทำงานเหมือนสตริงว่างในบริบทของสตริง และเหมือน
0 ในบริบทของตัวเลข
- เมื่อใช้สตริงในนิพจน์ตัวเลข จะมีการบังคับแปลงเป็นตัวเลข
- ถ้าสตริงไม่ได้ขึ้นต้นด้วยรูปแบบตัวเลขที่ถูกต้อง จะถูกมองเป็น
0
- ช่องว่างด้านหน้าจะถูกละเลย
- เมื่อเชื่อมสตริงเข้ากับตัวเลข ตัวเลขจะถูกแปลงเป็นสตริง
- รายละเอียดเพิ่มเติมดูได้ที่ gawk manual: Constant Expressions และ gawk manual: How awk Converts Between Strings and Numbers
อาร์เรย์
- อาร์เรย์ของ
awk เป็น associative array และทำงานเป็นคู่คีย์-ค่า
- คีย์อาจเป็นตัวเลขหรือสตริงก็ได้ แต่คีย์ที่เป็นตัวเลขจะถูกแปลงเป็นสตริงภายใน
- สามารถใช้อาร์เรย์หลายมิติได้เช่นกัน
- ในตัวอย่างมีการเก็บและเข้าถึงค่าด้วยคีย์สตริง เช่น
student["id"], student["name"]
- สามารถตรวจสอบการมีอยู่ของคีย์ได้ในรูป
"id" in student
- รายละเอียดเพิ่มเติมอยู่ที่ gawk manual: Arrays
แบบฝึกหัดและขั้นถัดไป
- บทนี้แนะนำอย่างย่อถึงรูปย่อของไวยากรณ์
awk, การกรอง, การแทนที่, การจัดการฟิลด์, การแปลงชนิดข้อมูล และอาร์เรย์
- บทถัดไปจะกล่าวถึง regular expression และความสามารถที่แนะนำในบทนี้จะยังถูกใช้ต่อในตัวอย่างต่าง ๆ
- คุณสามารถลองเปลี่ยนหมายเลขฟิลด์ หรือทดลองกับอินพุตรูปแบบอื่น เช่น หมายเลขฟิลด์ที่เป็นค่าลบหรือทศนิยม เพื่อให้คุ้นเคยกับไวยากรณ์มากขึ้น
- แอป TUI สำหรับฝึกแบบโต้ตอบติดตั้งได้จากรีโพซิทอรี AwkExercises และวิธีใช้อยู่ใน app_guide.md
- แบบฝึกหัดทั้งหมดรวมอยู่ใน Exercises.md และเฉลยอยู่ใน Exercise_solutions.md
1 ความคิดเห็น
ความคิดเห็นจาก Hacker News
ผมชอบ awk และใช้ค่อนข้างบ่อย หนึ่งในการใช้งานหลักคือใช้มันเหมือน sed แบบมีสถานะ
เช่น แมตช์เฉพาะเมื่อบรรทัดหนึ่งปรากฏหลังบรรทัดเฉพาะก่อนหน้า จึงมีประโยชน์เวลาทำ linter ชั่วคราว
ล่าสุดผมทำตัวตรวจสอบเพื่อหาไฟล์ migration ที่มี
CREATE INDEXซึ่งอาจเป็นปัญหากับตารางขนาดใหญ่มาก ๆ โดยไม่ได้ใส่CONCURRENTLYแต่คำสั่ง SQL อาจกินหลายบรรทัด ทำให้แมตช์แบบง่าย ๆ ได้ยากawk สามารถ ติดตามสถานะ ข้ามหลายบรรทัดได้ เช่น “กำลังอยู่ในคำสั่ง create”, “กำลังสร้าง index” ดังนั้นสคริปต์ที่ปะติดปะต่อแบบลวก ๆ ก็ทำงานได้ดีมาประมาณ 1 ปีแล้ว
ถ้าต้องการพิมพ์บรรทัดปัจจุบันเฉพาะเมื่อบรรทัดก่อนหน้าตรงกับแพตเทิร์นหนึ่ง ๆ ก็ทำได้ประมาณ
sed -ne 'x' -e '/PREV/ {x; /CURR/ p; x}'ตัวอย่าง:
echo -e "PREV\nCURR\nCURR\nCURR\nPREV\nRED" | sed -ne 'x' -e '/PREV/ {x; /CURR/ p; x}'จะพิมพ์แค่CURRนี่เป็นวิธีใช้ hold buffer ของ sed โดยใช้
-nเพื่อปิดการพิมพ์ตามค่าเริ่มต้น แล้วใช้pเพื่อพิมพ์เฉพาะบรรทัดที่ต้องการxจะสลับบรรทัดปัจจุบันกับ hold buffer และภายในบล็อก/PREV/ { ... }จะสลับกลับอีกครั้ง จากนั้นพิมพ์เฉพาะเมื่อบรรทัดปัจจุบันมีCURRxตัวสุดท้ายมีไว้เพื่อสลับกลับ เผื่อกรณีที่การแมตช์ซ้อนทับกันแน่นอนว่าสคริปต์ awk มีแนวโน้มจะเรียบง่ายและตรงไปตรงมากว่ามาก แต่ sed ก็ทำแบบนี้ได้เช่นกัน
เวลาที่ใช้เรียนรู้นี่อาจเอาไปลงกับ awk จะคุ้มกว่า แต่บทเรียน https://www.grymoire.com/Unix/Sed.html ดีมากจนผมเรียนรู้แทบทุกอย่างที่รู้เกี่ยวกับ sed จากที่นี่
ถ้าอ่านเธรดนี้อยู่ ก็น่าจะสนใจ “Ask HN: Share a shell script you like” เมื่อ 2 สัปดาห์ก่อนด้วย
มีคอมเมนต์ 78 รายการ จึงไม่ได้คึกคักเท่าที่คาดไว้ แต่ก็น่าเอาไว้ดูอ้างอิง: https://news.ycombinator.com/item?id=37112991
มีโพสต์จากปีก่อนด้วย: https://news.ycombinator.com/item?id=32467957 (374 คะแนน, 294 คอมเมนต์)
ผมยังคงสนใจ Awk อยู่เล็กน้อย ควบคู่กับ Lisp และอย่างอื่น ๆ และในปี 2022 ก็ทำ cppawk ขึ้นมา: https://www.kylheku.com/cgit/cppawk/about/
cppawk เพิ่ม ความสามารถด้านพรีโปรเซสเซอร์ ให้กับ Awk
มี loop macro ที่รองรับหลาย clause สามารถประกอบ clause เพื่อทำ parallel iteration หรือ Cartesian product iteration ได้ และผู้ใช้ก็ขยายเองได้ด้วย
แค่เขียน macro ง่าย ๆ 5 ตัวก็สามารถนิยาม clause ใหม่ได้
ถ้าใช้ Awk อยู่ก็น่าจะมีประโยชน์ มีเอกสารเป็น man page หลายหน้า และมี unit test ที่รันบน gawk กับ mawk ด้วย
อาจเป็นเพราะสัญชาตญาณผู้ดูแลระบบยุคเก่าของผมโผล่ออกมา แต่ผมไม่ค่อยเห็นข้อดีของ awk เมื่อเทียบกับการเขียนสิ่งเดียวกันด้วย Perl ตรง ๆ
ผมเห็น shell script แย่ ๆ ที่ผู้ดูแลระบบจูเนียร์ทำไว้เยอะมาก และทุกครั้งก็คิดว่า “ส่วนประมวลผลข้อความนี่ถ้าใช้ Perl คงสะอาดกว่านี้มาก”
สำหรับผม awk เป็นหนึ่งในไม่กี่ภาษาที่แม้จะวางทิ้งไว้หลายเดือน ก็ใช้เวลาแค่ 10 นาทีก็กลับมาจับทางได้อีก
มันมีความเป็น intuitive และเข้ากับเครื่องมือ command line ทั่วไปได้อย่างเป็นธรรมชาติ
แต่บทความนี้พูดถึง คำสั่งบรรทัดเดียว สั้น ๆ สำหรับงานชั่วคราว และในกรณีแบบนั้น sed/awk ดีกว่า Perl
ถ้ารู้ Perl อยู่แล้ว ก็ไม่จำเป็นต้องเรียนเครื่องมือเพิ่ม ใช้ Perl ต่อไปก็ได้
ตัวภาษาเองก็ “พอใช้ได้” แต่ใช้งานได้เพียงพอ
แน่นอนว่า Perl ก็ทำได้ทั้งหมด แต่ต้องเขียน boilerplate ที่ awk ให้มาฟรีเอง
ข้อดีของภาษา Perl สำหรับผมไม่ได้มากพอให้ทิ้ง awk และเพราะผมใช้ awk กับงานประมวลผลข้อมูลและปรับแต่งไฟล์แบบครั้งเดียว มากกว่าจะใช้เป็น “scripting” จึงไม่ได้โหยหาความลึกของ Perl
ถ้าต้องการฟีเจอร์ที่ลึกกว่านั้น ผมก็ไปใช้ที่อื่น
คนรุ่นนี้ไม่ได้เรียน Perl กัน จึงดูเหมือนกำลังค้นพบไอเดียการประมวลผล stream ขึ้นมาใหม่ผ่าน awk
awk เป็นไอเดียที่ยอดเยี่ยมตามมาตรฐานปลายทศวรรษ 1970 และเป็นนวัตกรรมจริง ๆ ที่คู่ควรแก่การเลียนแบบ
ต่อมา Perl ก็เลียนแบบและก้าวข้ามมันไป แต่กลับถูกลืม ดังนั้นการเห็น awk ถูกค้นพบใหม่จึงออกจะน่าเขินเล็กน้อย
สิ่งหนึ่งที่ไม่ค่อยมีคนรู้เกี่ยวกับ gawk คือโดยปกติมันมาพร้อม ส่วนขยาย ที่มีประโยชน์
สามารถเข้าถึงฟังก์ชันอย่าง
readdir(),ord(),chr(),gettimeofday(),sleep()ได้https://www.gnu.org/software/gawk/manual/html_node/Extension-Samples.html
คำสั่ง awk แบบบรรทัดเดียวทรงพลังจริง ๆ
คำถามที่ยากคือคุ้มไหมที่จะลงทุนกับการเขียนโปรแกรม awk ที่ซับซ้อนกว่าเดิม
ถ้างานประมวลผลต้องใช้ตรรกะที่ซับซ้อน awk ก็มีให้ แต่ให้มาในรูปแบบสั้น ๆ อ่านยาก ๆ สไตล์ยุคคอมพิวเตอร์ยุคแรก
แต่ถ้าเลือกทางเลือกสมัยใหม่ ก็มีภาระของมันเอง โดยเฉพาะบางอย่างอย่าง pandas ที่อาจไม่ค่อย intuitive และยังอาจมีปัญหาเรื่องประสิทธิภาพด้วย
แม้แต่ไฟล์ฟังก์ชัน common สำหรับใช้ส่วนตัวก็ยังไม่รู้สึกว่ารองรับดีนัก และดูเหมือนไม่มีวิธีที่เหมาะ ๆ ในการนำไลบรารี third-party มาใช้
พอเริ่มต้องมี helper function และเริ่มแยกเป็นหลายบรรทัด ปกติก็จะย้ายไป Python
แล้วโปรแกรมก็ใหญ่ขึ้น 2–3 เท่า จนต้องถอนหายใจ
Ruby เป็นตัวแทน awk ที่ยอดเยี่ยม แต่ถ้าเพื่อนร่วมงานไม่รู้จัก Ruby ก็คาดหวังให้ดูแลรักษาต่อได้ยาก
เดี๋ยวนี้พอเอาคำสั่งอ่านยากพวกนั้นไปแปะให้ AI มันก็อธิบายทีละขั้นตอนได้ค่อนข้างดี เลยพอรับได้มากขึ้น
ถึงอย่างนั้นเพราะเรื่องความสามารถในการทำ unit test ผมยังชอบ Python อีกไม่กี่บรรทัดมากกว่า แต่สำหรับงานแปลงข้อมูลเร็ว ๆ บางครั้งก็ไม่จำเป็นต้องมี unit test ตั้งแต่แรก
เปิดตัวอีบุ๊กเวอร์ชันใหม่ของ “CLI text processing with GNU awk”
สามารถเรียนรู้คำสั่ง
GNU awkตั้งแต่ระดับเริ่มต้นถึงขั้นสูงแบบเป็นขั้นเป็นตอน ผ่านตัวอย่างและแบบฝึกหัดหลายร้อยรายการ ครอบคลุมเชิงลึกทั้งการประมวลผลฟิลด์ การกรอง การจัดการหลายไฟล์ วิธีแก้ปัญหาที่พึ่งพาหลายเรคอร์ด การเปรียบเทียบเรคอร์ดและฟิลด์ระหว่างไฟล์ การหาข้อมูลซ้ำโดยยังรักษาลำดับอินพุตไว้ regex และอื่น ๆPDF/EPUB: https://learnbyexample.gumroad.com/l/gnu_awk (ฟรีจนถึง 31 สิงหาคม 2023)
เวอร์ชันเว็บ: https://learnbyexample.github.io/learn_gnuawk/
ซอร์ส Markdown และไฟล์ตัวอย่าง: https://github.com/learnbyexample/learn_gnuawk
แอป TUI แบบโต้ตอบสำหรับฝึกทำแบบฝึกหัด: https://github.com/learnbyexample/TUI-apps/blob/main/AwkExercises
ชุดบันเดิล Magical one-liners ที่รวมคำสั่งบรรทัดเดียวของ grep, sed, awk, perl, ruby ราคา $5: https://learnbyexample.gumroad.com/l/oneliners/new_awk_release, บันเดิลอีบุ๊กครบทั้ง 13 เล่ม ราคา $12: https://learnbyexample.gumroad.com/l/all-books/new_awk_release
ฟีดแบ็กใด ๆ ไม่ว่าจะเป็นคำผิด ข้อผิดพลาดในโค้ด ส่วนที่ใช้ได้ดีหรือใช้ได้ไม่ดี ล้วนช่วยได้มาก
การถกเถียงก่อนหน้านี้มี https://news.ycombinator.com/item?id=15549318 และ https://news.ycombinator.com/item?id=22758217
มันอาจมีประโยชน์พอให้จ่าย $5 หรือ $15 ก็ได้ แต่ก็อาจไม่ต่างจากสิ่งที่ผมเก็บไว้แล้วในไฟล์คำสั่งบรรทัดเดียวส่วนตัว เลยลังเลที่จะจ่ายเงินเพื่อเช็กดู
สงสัยว่าเวอร์ชันเว็บจะยังคงฟรีต่อไปหลังวันที่ 31 สิงหาคมด้วยหรือไม่
เมื่อก่อนเคยทำกอล์ฟ วาดรูปหัวใจด้วย AWK ไว้: https://gist.github.com/auselen/906a53b47a7d616b080dbef85eb8f776
99.9% ของการใช้ awk คือใช้แยกบรรทัดพร้อมทิ้งช่องว่างต่อเนื่อง
เช่น:
echo "key: value" | awk '{print $1}'ถ้ามีทางเลือกที่ง่ายกว่านี้ก็คงดี
เขียนด้วย Nim แต่ก็อาจไม่ใช่อุปสรรคใหญ่ และเครื่องมืออื่น ๆ ใน
bu/ก็น่าสนใจได้เช่นกันcutก็ทำได้:echo "key: value" | cut -wf 2แต่จะง่ายกว่าจริงไหมยังเถียงกันได้
ลองตรวจดูแล้ว GNU cut ไม่มี
-wจึงเป็นของ BSD เท่านั้นสุดท้ายคงใช้ awk ดีกว่า
ทั้งสองเป็นทางเลือกแทน cut/awk และรองรับการแยกตาม regex ด้วย แต่เท่าที่จำได้ไม่ตัดช่องว่างหัว/ท้าย
เครื่องมือที่ผมทำเอง https://github.com/learnbyexample/regexp-cut เป็นเครื่องมือคล้าย
cutที่ใช้awkเพื่อให้แยกตาม regex, ใช้ดัชนีติดลบ ฯลฯ ได้ และด้วยพฤติกรรมพื้นฐานของ awk จึงจัดการช่องว่างหัว/ท้ายได้ด้วยecho "key: value" | awk '{print $2}'มากกว่าก่อนหน้านี้ผมเคยเขียน สคริปต์ diff2html ที่พอร์ตมาจาก bash ด้วย awk และด้วยเหตุผลที่ชัดเจน มันเร็วกว่าเยอะ
ฝั่ง awk อ่านง่ายกว่าสคริปต์ bash มาก และผมสามารถเรียนภาษา ดีบัก ทำความเข้าใจบั๊ก แล้วแก้ได้ภายในคืนเดียว
ไม่รู้ว่านี่เป็นวิธีเขียนแบบ awk ที่เป็นสำนวนปกติหรือเปล่า แต่รู้สึกว่าเป็นภาษาที่ดีจริง ๆ
https://github.com/berry-thawson/diff2html/blob/master/diff2html.sh