Unix03.txt ----------- รายละเอียดคำสั่งของ Unix และ bash - คำสั่ง test; คำสั่งภายในของ bash และโปรแกรมอรรถประโยชน์ของ Unix - คำสั่ง read - คำสั่งภายในของ bash - คำสั่ง date - โปรแกรมอรรถประโยชน์ของ Unix คำสั่ง test --------- test - Evaluates an expression (ประมวลผลนิพจน์) -- โปรแกรมอรรถประโยชน์ของ Unix :: รูปแบบการใช้งาน :: test <นิพจน์> # รูปแบบแรกใช้สำหรับ command line [ <นิพจน์> ] # รูปแบบที่สองนิยมใช้ใน shell script :: คำอธิบาย (Description) :: test ใช้สำหรับประมวลผลนิพจน์ (expression) และคืนสถานะของการประมวลผลนิพจน์นั้นว่ามีค่าเป็น “จริง” หรือ “เท็จ” คำสั่ง test มีรูปย่อเป็น [ <นิพจน์> ] ซึ่งเป็นที่นิยมใช้มากกว่า นิพจน์ที่ใช้งานได้มีหลายกลุ่ม ตัวอย่างเช่น การทดสอบและการเปรียบเทียบสายอักขระ ------------------------------- string เป็นจริงหาก string ที่ต้องการทดสอบไม่ใช่ string ว่าง -n string เป็นจริงหาก string มีความยาวมากกว่าศูนย์ -z string เป็นจริงหาก string มีความยาวเป็นศูนย์ string1 = string2 เป็นจริงหาก string1 และ string2 เป็นข้อความเดียวกัน string1 != string2 เป็นจริงหาก string1 และ string2 เป็นข้อความที่ต่างกัน การเปรียบเทียบจำนวนเต็ม ------------------- -eq เท่ากับ (equal to) -ge มากกว่าหรือเท่ากับ (greater than or equal to) -gt มากกว่า (greater) -le น้อยกว่าหรือเท่ากับ (less than or equal to) -lt น้อยกว่า (less than) -ne ไม่เท่ากับ (not equal to) การทดสอบชนิดของแฟ้ม ------------------ -b <ชื่อแฟ้ม> เป็นจริงหากเป็นแฟ้มที่มีอยู่จริงและเป็นแฟ้มแทนอุปกรณ์ชนิด block special file -c <ชื่อแฟ้ม> เป็นจริงหากเป็นแฟ้มที่มีอยู่จริงและเป็นแฟ้มแทนอุปกรณ์ชนิด character special file -d <ชื่อไดเรกทอรี> เป็นจริงหากเป็นไดเรกทอรีที่มีอยู่จริง -e <ชื่อ> เป็นจริงหากชื่อนั้น, ชื่อแฟ้ม หรือชื่อไดเรกทอรีที่กำหนดมีอยู่จริง -f <ชื่อแฟ้ม> เป็นจริงหากเป็นแฟ้มธรรมดาที่มีอยู่จริง -h <ชื่อแฟ้ม> เป็นจริงหากชื่อเป็น แฟ้มที่มีอยู่จริงและเป็น symbolic link การทดสอบขนาดของแฟ้ม ------------------- -s <ชื่อแฟ้ม> เป็นจริงหากเป็นแฟ้มที่มีอยู่จริงและมีขนาดมากกว่า 0 ไบต์ การทดสอบสิทธิในการใช้งานแฟ้ม ------------------------- -r <ชื่อแฟ้มหรือชื่อไดเรกทอรี> เป็นจริงหากเป็นแฟ้มที่มีอยู่จริงและผู้ใช้มีสิทธิ "read" แฟ้มนั้น -w <ชื่อแฟ้มหรือชื่อไดเรกทอรี> เป็นจริงหากเป็นแฟ้มที่มีอยู่จริงและผู้ใช้มีสิทธิ "write" แฟ้มนั้น ในกรณีที่เป็น-- --ชื่อไดเรกทอรีหมายถึงผู้ใช้มีสิทธิสร้างและลบแฟ้มในไดเรกทอรีนั้น -x <ชื่อแฟ้มหรือชื่อไดเรกทอรี> เป็นจริงหากเป็นแฟ้มที่มีอยู่จริงและผู้ใช้มีสิทธิ "execute" ในกรณีที่เป็น-- --ชื่อไดเรกทอรีหมายถึงผู้ใช้มีสิทธิอ่านรายชื่อแฟ้มในไดเรกทอรีนั้น การเปรียบเทียบแฟ้ม ---------------- <ชื่อแฟ้ม> -ef <ชื่อแฟ้ม> เป็นจริงหากแฟ้ม file1 และ file2 เป็นแฟ้มแทนอุปกรณ์เดียวกัน และมี i-node เดียวกัน <ชื่อแฟ้ม> -nt <ชื่อแฟ้ม> เป็นจริงหากมีการแก้ไข (modified) แฟ้ม file1 "หลัง" แฟ้ม file2 <ชื่อแฟ้ม> -ot <ชื่อแฟ้ม> เป็นจริงหากมีการแก้ไข (modified) แฟ้ม file1 "ก่อน" แฟ้ม file2 Argument ของคำสั่ง test เป็นนิพจน์ที่ประกอบด้วยเงื่อนไขที่ต้องการทดสอบ ในกรณีที่มีเงื่อนไขตั้งแต่สองเงื่อนไขขึ้นไป กำหนด Logical operator ดังนี้ Logical operator ---------------- ! นิเสธ (NOT) -a AND -o OR เนื่องจาก AND มีลำดับความสำคัญสูงกว่า OR หากต้องการเปลี่ยนลำดับให้ใช้วงเล็บจัดกลุ่ม แต่เนื่องจากวงเล็บเป็นอักขระพิเศษของเชลล์ เมื่อจะใช้งานจึงต้องกำกับด้วย \ เพื่อป้องกันเชลล์ขยายความหมาย และในทำนองเดียวกันหากมีการใช้อักขระพิเศษอืนใด ต้องทำการกำกับอักขระพิเศษนั้น เพื่อป้องกันเชลล์ทำการขยายความอักขระพิเศษนั้น ก่อนส่งให้ test ดำเนินการ และเนื่องจากองค์ประกอบแต่ละส่วนของนิพจน์ เช่นเงื่อนไข สายอักขระ ตัวแปร ต่างเป็น argument ของคำสั่ง test ดังนั้นจึงต้องใช้เว้นวรรคแยกแต่ละส่วนออกจากกัน การประยุกต์ใช้งานคำสั่ง test ----------------------- คำสั่ง test สามารถทำงานได้ทั้งจาก command line และ shell script แต่โดยทั่วไปแล้วคำสั่งนี้มีที่ใช้ใน shell script มากกว่า โดยใช้เป็นเงื่อนไขสำหรับโครงสร้างควบคุมการทำงานแบบมีทางเลือก และแบบทำซ้ำ การใช้งานคำสั่ง test จาก command line โดยทั่วไปมักใช้ในการทดสอบว่าเงื่อนไขที่สนใจให้ผลลัพธ์เป็นอย่างไรก่อนที่จะนำไปใช้ใน shell script แต่เนื่องจากคำสั่ง test ไม่มีการแสดงผล ดังนั้นผลการทำงานจึงต้องตรวจสอบจากสถานะการทำงานที่คำสั่งนั้นคืนให้แก่เชลล์ ซึ่งเรียกว่า return code คำสั่งทุกคำสั่งที่มีการเรียกให้ทำงานในระบบปฏิบัติการ Unix เมื่อจบการทำงานจะคืน return code ให้แก่ parent process (เชลล์ที่เป็นผู้เรียก) ซึ่งเชลล์จะจัดเก็บไว้ในตัวแปร $?, return code เป็นจำนวนเต็ม โดย 0 แทนการทำงานที่เสร็จสิ้นสมบูรณ์ เมื่อเรียกใช้งานคำสั่งใดแล้ว สามารถตรวจสอบสถานะการทำงานได้จากตัวแปรนี้ เช่น $ ls hello.c test.c $ ls -l hello.c # ขอดูรายละเอียดของแฟ้มที่มี -rw------- 1 jira staff 89 Jan 11 12:58 hello.c $ echo $? # ตรวจสอบสถานะการทำงานของคำสั่งในตัวแปร $? 0 # return code = 0 แสดงว่าคำสั่งที่แล้วทำงานเสร็จสมบูรณ์ $ ls -l xyz # ขอดูรายละเอียดของแฟ้มที่ไม่มี ls: cannot access xyz: No such file or directory $ echo $? # return code = 2 แสดงว่ามีปัญหาในการทำงาน 2 นำมาใช้ในการศึกษาทำความเข้าใจเงื่อนไข นิพจน์เปรียบเทียบ และนิพจน์ตรรศาสตร์ $ test 4 -gt 3 # 4 > 3? $ echo $? 0 # ผลการเปรียบเทียบเป็น "จริง" $ test 3 -nq 3 # 3 <> 3? $ echo $? 1 # ผลการเปรียบเทียบเป็น "เท็จ" หมายเหตุ ------- นอกจากคำสั่ง test ที่เป็นโปรแกรมอรรถประโยชน์ของ Unix แล้ว ยังมีคำสั่ง test ที่เป็นคำสั่งภายในของ bash ด้วย ซึ่งมีการทำงานเหมือนกัน แต่ test ของ bash ไม่มีรูปย่อเป็นวงเล็บก้ามปูเท่านั้น และเนื่องจาก test เป็นคำสั่งภายในของเชลล์ จึงมีลำดับความสำคัญในการทำงานสูงสุด ดังนั้นจึงไม่ควรตั้งชื่อโปรแกรมที่เขียนขึ้นเองเป็น test เพราะจะไม่สามารถเรียกใช้งานได้ เมื่อป้อนชื่อโปรแกรมเป็น test จะได้การทำงานของคำสั่ง test ของเชลล์แทน จึงดูเหมือนโปรแกรมที่พัฒนาขึ้นไม่ทำงาน สร้างความสับสนให้แก่ผู้เริ่มเขียนโปรแกรมได้มาก read คำสั่งภายในของเชลล์ --------------------- read รายชื่อตัวแปร ... read อ่านสายอักขระ 1 บรรทัดจาก standard input และทำการแยกออกเป็น field read อ่านข้อความ 1 บรรทัดจาก standard input หรือจาก file descriptor ของแฟ้มที่กำนดด้วย option -u ข้อความที่อ่านได้จะถูกแยกออกเป็นคำ คำแรกจะนำกำหนดให้กับชื่อตัวแปรตัวแรก คำที่สองจะนำกำหนดให้กับชื่อตัวแปรตัวที่สอง เป็นเช่นนี้เรื่อยไป ในกรณีที่เหลือจำนวนคำมากกว่าจำนวนตัวแปร คำที่เหลือทั้งหมดจะถูกใช้กำหนดให้กับตัวแปรตัวสุดท้าย การแยกข้อความออกเป็นคำทำโดยใช้เครื่องหมายวรรคตอนที่กำหนดไว้ในตัวแปร IFS (Internal Field Separator - โดยทั่วไปได้แก่ วรรค และคั่นหน้า) ในกรณีที่ไม่ได้กำหนดชื่อตัวแปร ระบบจะสร้างตัวแปรชื่อ REPLY และเก็บข้อความทั้งบรรทัดในตัวแปรนี้ bash รุ่นปัจจุบัน คำสั่ง read มี option ให้ใช้มากมาย สนใจ help read -p prompt - กำหนดข้อความเป็น prompt ประกอบการรับ input -t timeout - กำหนดเวลาสูงสุดในการรอรับข้อความ หากสนใจใช้งาน ศึกษาเพิ่มเติมได้จาก help read คำสั่ง date - โปรแกรมอรรถประโยชน์ของ Unix -------------------------------------- date : แสดงเวลาหรือตั้งเวลาของระบบคอมพิวเตอร์ใหม่ ผู้ใช้ทั่วไปจะสามารถขอดูเวลาของระบบได้เพียงอย่างเดียว ผู้ที่จะสามารถตั้งเวลาระบบใหม่ได้คือผู้ดูแลระบบ (ผู้ใช้ root) เท่านั้น การแสดงเวลาของระบบสามารถทำได้หลายแบบ รูปแบบโดยปริยายคือ วันและเวลาท้องถิ่น $ date | Fri Mar 27 07:32:50 ICT 2015 | ชื่อย่อมาตรฐานของ "เขตเวลา" (Time Zone) หากต้องการให้แสดงวันเวลาตามรูปแบบมาตรฐาน RFC-2822 กำหนดด้วย option -R เช่น $ date -R Fri, 27 Mar 2015 07:32:54 +0700 | เวลาท้องถิ่น "เร็ว" กว่าเวลามาตรฐาน UTC 7 ชั่วโมง และหากต้องการให้แสดงเวลามาตรฐาน Coordinated Universal Time (UTC) กำหนดด้วย option -u เช่น $ date -u Fri Mar 27 03:47:31 UTC 2015 เนื่องจากคำสั่ง date แสดงทั้งวันและเวลาพร้อมกัน ในบางกรณีผู้ใช้อาจต้องการเฉพาะวัน หรือเฉพาะเวลา จึงอนุญาตให้กำหนดรูปแบบสำหรับการแสดงผล หรือ format ได้ รูปแบบสำหรับการแสดงผลมีสามส่วนคือ เครื่องหมาย +, เครื่องหมาย %, และอักษรกำหนดรูปแบบ เช่น %H ชั่วโมง, 0 - 24 %d วันที่ %I ชั่วโมง, 0 - 12 %m เลขเดือน, 1 - 12 %M นาที %Y ปี ค.ศ., 4 หลัก %S วินาที %y ปี ค.ศ., เฉพาะ 2 หลักท้าย format เหล่านี้มีประโยชน์จะมีประโยชน์มากในการเลือกข้อมูลเฉพาะอย่าง สำหรับกำหนดให้กับตัวแปร หรือส่งต่อไปใน Pipeline และนอกจาก format ที่กล่าวถึงแล้วนี้ ยังมี format อื่นๆ อีกมาก สนใจใช้งานอ่านได้จาก online manual page ตัวอย่างการใช้งาน format --------------------- $ date +%Y 2015 การใช้งานจริงนิยมใช้ใน pipeline หรือทำ command substitution เพื่อนำค่ามากำหนดให้กับตัวแปร ภาคผนวก ๑: เวลามาตรฐานในกลุ่มประเทศอาเซียน --------------------------------------------------------------------------------- ประเทศ รหัสเวลา ชื่อเขตเวลา เวลาชดเชย --------------------------------------------------------------------------------- บรูไน ดารุสซาลาม BNT Brunei Darussalam UTC +8:00 กัมพูชา ICT Indochina Time UTC +7:00 ลาว ICT Indochina Time UTC +7:00 มาเลเซีย MYT Malaysian Time UTC +8:00 เมียนมาร์ (พม่า) MMT Myanmar Time UTC +6:30 ฟิลิปปินส์ PHT Philipines Time UTC +8:00 สิงคโปร์ SGT Singapore Time UTC +8:00 เวียดนาม ICT Indochina Time UTC +7:00 ไทย ICT Indochina Time UTC +7:00 อินโดนีเซีย WIB Western Indonesian Time UTC +7:00 WIT Eastern Indonesian Time UTC +9:00 WITA Central Indonesian Time UTC +8:00 --------------------------------------------------------------------------------- หมายเหตุ 1. อินโดนีเซียเป็นหมู่เกาะ มีความยาวไปตามเส้นศูนย์สูตรมาก จึงต้องมีเวลามาตรฐานหลายแบบให้เหมาะสมกับแต่ละภูมิภาค 2. ดูรายละเอียดเพิ่มเติมได้จาก http://www.timeanddate.com/time/zones ภาคผนวก ๒: ในกรณีที่ผู้ดูแลระบบต้องการตั้งเวลาใหม่ กำหนดด้วย option -s สำหรับผุ้ใช้ทั่วไปหากนำ option นี้มาใช้ตั้งเวลาจะได้ error message เช่น $ date -s 01/01/15 # หรือ date -s 01/01/2015 date: cannot set date: Operation not permitted # ไม่สามารถตั้งเวลาได้ เนื่องจากเป็นผู้ใช้ที่ไม่ได้รับอนุญาต Thu Jan 1 00:00:00 ICT 2015 # คือ Thu Jan 1 00:00:00 ICT 2015 ได้