/ BasicKnowledge

[365 วันแห่งโปรแกรม #day58] Date/Time (ตอนที่ 2)

วันที่ห้าสิบแปดของ ‪#‎365วันแห่งโปรแกรม วันนี้เราคงยังอยู่ที่เรื่อง Date/Time ครับ แต่ครั้งนี้จะเกี่ยวข้องกับ IT มากขึ้นละ


Calendar date

ครั้งที่แล้วเราคุยกันไปว่าปฏิทินเนี่ยเกิดขึ้นมาเพื่อใช้ในการพูดถึงเวลาที่มีขนาดใหญ่มาก หรือเพื่อการบริหารจัดการต่างๆ เวลาเราจะพูดถึงวันปฏิทิน หรือ Calendar date เจ้าวันปฏิทินเนี่ยก็คือการบอกวันที่และ/หรือเวลา เช่น 1 มกราคม 2015 อะไรแบบนี้ เพียงเท่านี้เราก็จะเข้าใจตรงกันแล้วว่าหมายถึงเมื่อไหร่

อย่างไรก็ตามเราสามารถเขียนวันปฏิทินได้หลายรูปแบบ (date format) เช่น วันเดือนปี ปีเดือนวัน เดือนปีวัน เป็นต้น ซึ่งก็ขึ้นอยู่กับธรรมเนียมของท้องถิ่นนั้นๆ

ความแตกต่างของการเขียนวันปฏิทินทำให้จำเป็นต้องมีการกำหนดมาตรฐานการสำหรับเอาไปใช้ในการแลกเปลี่ยนข้อมูลในระบบคอมพิวเตอร์ เพื่อป้องกันความสับสนระหว่างต้นทางกับปลายทาง

ISO 8601

ISO 8601 เป็นมาตรฐานของ date format สำหรับใช้ในการสื่อสารข้อมูล ซึ่งในมาตรฐานนี้จะประกอบด้วยทั้งวันที่และเวลา

ISO 8601 นั้นจะใช้ปฏิทินเกรกอเรียน ระบบเวลาแบบ 24 ชั่วโมง และอาจจะมีการกำหนด time zone ด้วยก็ได้ โดยในการใช้งานจะมีรูปแบบดังนี้

ส่วนของวันที่
การระบุปี (Year)

ใน ISO 8601 จะใช้ตัวเลข 4 ตัวเพื่อระบุปี ซึ่งทำให้มีค่าที่เป็นไปได้ตั้งแต่ 0000 ถึง 9999 โดย 0000 นั้นจะเท่ากับ 1 BC (Before Christ) อย่างไรก็ตามค่าตั้งแต่ 0000 ถึง 1582 ไม่อนุญาตให้ใช้โดยทั่วไปในมาตรฐานนี้ เนื่องจากไม่ได้อยู่ในปฏิทินเกรกอเรียนซึ่งอาจจะทำให้วันที่ผิดพลาดตามหลักปฏิทิน

1990 - ถูกต้องตาม ISO 8601
1550 - ผิดหลัก ISO 8601 แต่อนุโลมให้ใช้ได้ถ้ามีการตกลกันดีแล้ว

ถ้าต้องการกล่าวถึงปีก่อน 0000 หรือหลัง 9999 มาตรฐานนี้ก็มีส่วนขยายให้ โดยให้ใส่เครื่องหมาย + หรือ - นำหน้าปี ซึ่ง +0000 จะหมายถึง 1 BC -0001 จะหมายถึง 2 BC หรือถ้าจะใช้ปีที่มากกว่า 9999 ก็ใส่เครื่องหมาย + แล้วเพิ่มจำนวนหลักเข้าไปได้เลย

+0000  - 1 BC
-0001  - 2 BC
+10000 - 10000
การเขียนวันปฏิทิน (Calendar date)

วันปฏิทินใน ISO 8601 จะขึ้นด้วยปี 4 หลัก ([YYYY]) ตามด้วยเดือนเป็นเลข 2 หลัก ([MM]) สุดท้ายตามด้วยวันที่เป็นเลข 2 หลก ([DD]) โดยอาจจะใช้ hyphen (-) คั่นระหว่างแต่ละค่าก็ได้ (extended format)

นอกจา้นี้ในมาตรฐานนี้ยังรองรับการเขียนวันปฏิทินที่มี precision ต่ำกว่าระดับวัน เช่นบอกแค่ ปีและเดือน ปีเฉยๆ หรือแค่ศตวรรษ (100 ปี) ก็ได้

2010-09-19 - YYY-MM-DD
20100919   - YYYYMMDD
2010-09    - YYYY-MM
201009     - YYYYMM ไม่สามารถใช้ได้ เพราะอาจจะทำให้สับสนกับ YYMMDD ซึ่งเป็นที่นิยมใช้มากกว่า (ปัจจุบัน YYMMDD ถูกถอดออกจากมาตรฐานแล้ว)
2010       - YYYY
20         - 2000-2099
การเขียน Week date

Week date คือรูปแบบการเขียนวันที่แบบสนใจเฉพาะลำดับที่ของสัปดาห์และปีเท่านั้น มีการใช้รูปแบบนี้อย่างกว้างขวางในสายงานธุรกิจต่างๆ ใน ISO 8601 กำหนดว่าจะต้องขึ้นด้วยปี 4 หลัก ([YYYY]) ตามด้วยตัวอักษร W และตามด้วยลำดับที่ของสัปดาห์ ([ww]) ซึ่งมีค่าตั้งแต่ 01 ถึง 53 นอกจากนี้ยังอาจจะมีการใส่วันที่ของสัปดาห์ลงไปด้วย 1 หลัก (1-7 จันทร์-อาทิตย์)

2008-W13    - YYYY-Www
2008W13     - YYYYWww
2008-W13-1  - YYYY-Www-D
2008W131    - YYYYWwwD
การเขียน Ordinal date

Ordinal date เป็นการเขียนวันที่อีกรูปแบบหนึ่งซึ่งระบุแค่ปี และวันที่ของปี (1-366) โดยใน ISO 8601 กำหนดให้เขียนดดยขึ้นด้วยปี 4 หลัก ([YYYY]) และตามด้วยวันที่ของปี 3 หลัก ([DDD])

1981-095 - YYYY-DDD มีค่าเป็น 1982-04-05 
1981095  - YYYYDDD มีค่าเป็น 1982-04-05 
ส่วนของเวลา

ISO 8601 นั้นจะใช้เวลาแบบ 24 ชั่วโมงเสมอ โดยรูปแบบทั่วไปจะเขียนเป็น ชั่วโมงนาทีวินาที ([hh][mm][ss]) หรืออาจจะใส่เครื่องหมาย colon (:) คั่นระหว่างแต่ละค่าก็ได้ (extended format) [hh]:[mm]:[ss]

[hh] refers to a zero-padded hour between 00 and 24 (where 24 is only used to denote midnight at the end of a calendar day).

[mm] refers to a zero-padded minute between 00 and 59.

[ss] refers to a zero-padded second between 00 and 60 (where 60 is only used to denote an added leap second).

ตัวอย่าง

hhmmss   - 134730 
hh:mm:ss - 13:47:30

นอกจากนี้เรายังสามารถตัดทอนส่วนของ วินาทีออกไปก็ได้หากไม่ต้องการใช้ก็จะได้เป็น [hh][mm] หรือหากต้องการแค่ชั่วโมงก็ตัดเหลือแค่ [hh] หรือถ้าต้องการเพิ่มความละเอียดอีกก็สามารถใส่มิลลิวินาทีลงได้ด้วยโดยใส่เครื่องหมาย . ตามหลังวินาทีและตามด้วยมิลลิวินาที 3 หลัก ([hh]:[mm]:[ss])

hh           - 1347
hhmm         - 1347
hh:mm        - 13:47
hhmmss.sss   - 134730.123
hh:mm:ss.sss - 13:47:30.123
เขตเวลา (Time zone)

เขตเวลาใน ISO 8601 นั้นจะมีค่าปริยายเป็นไม่กำหนด หรือ local time แต่ถ้าต้องการกำหนดเขตเวลาก็สามารถกำหนดเป็น UTC หรือ offset จากเขตเวลา UTC ได้

####### UTC

เราสามารถกำหนดว่าเวลานี้เป็นไปตามเขตเวลา UTC ได้โดยการเติมตัวอักษร Z หลังเวลา เช่น 9:30 UTC ต้องเขียนเป็น 09:30Z หรือ 0930Z เป็นต้น

####### Offset จาก UTC

หากเราไม่ต้องการใช้เวลาตามเขต UTC +0 เราก็สามารถใส่ Offset ลงได้ไป โดยใส่เครื่องหมาย + หรือ - แล้วตามด้วยจำนวนชั่วโมงและจำนวนนาที (±hh:mm หรือ ±hhmm หรือ ±hh) เช่นถ้าต้องการบอกว่าเป็นเวลา 7:15 ตามเวลาประเทศไทยก็สามารถเขียนได้ว่า 07:15+07

เราสามารถแทนเขตเวลา UTC +0 ด้วย Z หรือจะเขียนเป็น Offset ก็ได้ (+00 +00:00 +0000) แต่ห้ามใช้เครื่องหมาย - กับเขตเวลานี้ (ไม่สามารถใส่เป็น -00 -00:00 -0000 ได้)

การใส่วันที่และเวลาร่วมกัน

ที่กล่าวมาข้างต้นนั้นเป็นการเขียนวันที่ หรือเวลา ตามมาตรฐาน ISO 8601 แต่เรายังสามารถรวมทั้งสองอย่างเข้าด้วยกันได้โดยทำการเขียนวันที่ไว้ข้างหน้าแล้วตามด้วยตัวอักษร T ตามด้วยเวลา เช่น 2015-08-27T15:30+7:00

*ตัวอักษร T ใช้บอกว่าหลังจากนี้จะเป็นส่วนของเวลา

*ทั้งวันที่ เวลา และเขตเวลา ถ้าจะเขียนแบบ basic (ไม่มีเครื่องหมาย - หรือ : คั่น) ก็ต้องเขียนแบบ basic ทั้งหมด ถ้าจะเขียนแบบ extended (มีเครื่องหมาย - หรือ : คั่น) ก็ต้องใช้ extended ทั้งหมด

Duration

ที่ผ่านมาเราพูดถึงเรื่องการบอกวันที่หรือเวลา แต่ยังมีอีกเรื่องหนึ่งที่สำคัญพอๆ กันนั่นก็คือเรื่องระยะเวลา Duration หมายถึงระยะเวลาแบบไม่ได้กำหนดจุดเริ่มต้นและจุดสิ้นสุด แต่จะบอกแค่ขนาดของช่วงเวลาว่ากี่ปี กี่ชั่วโมง อะไรแบบนี้ ใน ISO 8601 ก็มีการตะเตรียมวิธีการเขียน Duration เอาไว้ให้แล้ว โดยจะมีตัวอักษรเพื่อสื่อความหมายเพิ่มเข้ามาดังนี้

P ใช้ในการระบุว่าต่อไปนี้คือ Duration นะ เขียนไว้เป็นตัวแรกสุดเสมอ
Y ใช้ระบุว่าตัวเลขก่อนหน้านี้คือจำนวนปี
M ใช้ระบุว่าตัวเลขก่อนหน้านี้คือจำนวนเดือน
W ใช้ระบุว่าตัวเลขก่อนหน้านี้คือจำนวนปีสัปดาห์
D ใช้ระบุว่าตัวเลขก่อนหน้านี้คือจำนวนวัน
T เป็นตัวเดียวกับ T ในเรื่องที่แล้ว คือใช้ในการคั่นระหว่างหน่วยเวลาใหญ่ (เปี เดือน วัน) กับหน่วยเวลาย่อย (ชั่วโมง นาที วินาที)
H ใช้ระบุว่าตัวเลขก่อนหน้านี้คือจำนวนชั่วโมง
M ใช้ระบุว่าตัวเลขก่อนหน้านี้คือจำนวนนาที (M ตัวนี้ต้องอยู่หลัง T เสมอ ไม่งั้นจะถือว่าเป็น เดือน)
S ใช้ระบุว่าตัวเลขก่อนหน้านี้คือจำนวนวินาที

เวลาเขียนจะเขียนในรูปแบบ P[n]Y[n]M[n]DT[n]H[n]M[n]S หรือ P[n]W เมื่อ [n] คือตัวเลขที่ใช้ระบุจำนวนของค่าต่างๆ ตัวอย่างเช่น P3Y6M4DT12H30M5S หมายถึง 3 ปี 6 เดือน 4 วัน 12 ชั่วโมง 30 นาที 5 วินาที สำหรับในหลักไหนที่มีค่าเป็น 0 สามารถตัดตัวอักษรประจำหลักนั้นทิ้งไปได้เลย เช่น P3Y หมายถึงระยะเวลา 3 ปี (ถ้าไม่ต้องการใส่เวลาก็ให้ตัด T ทิ้งไปด้วย แต่ห้ามตัด P ทิ้งเด็ดขาด)

นอกจากนี้เรายังสามารถใส่จำนวนที่เป็นทศนิยมได้ด้วยเช่น P0.5Y คือครึ่งปี เครื่องหมายที่ใช้คั่นระหว่างจำนวนเต็มและทศนิยมสามารถใช้ได้ทั้ง full stop (.) และ comma (,)

อีกทั้งเรายังสามารถใส่จำนวนเกิดจีดจำกัดในหน่วยนั้นๆ ได้ เช่น PT36H สามารถใช้แทน P1DT12H ได้

สุดท้ายถ้าเรายังอยากเขียนเป็นรูปแบบวันที่และเวลาก็ทำได้ตามปกติเลย แค่ใส่ตัว P นำหน้าไป ก็จะถือว่าเป็น Duration เช่นกัน เช่น P0003-06-04T12:30:5 จะมีค่าเท่ากับ P3Y6M4DT12H30M5S อย่างไรก็ตามการเขียนด้วยวิธีนี้จะทำให้เราไม่สามารถใส่จำนวนเกินความสามารถของหลักนั้นๆ ได้ เช่น เราไม่สามารถใส่ hour เป็น 25 ได้ และไม่สามารถใส่เป็นทศนิยมได้

Time interval

Time interval เป็นระยะเวลาอีกแบบหนึ่งที่มีจุดเริ่มต้นและสิ้นสุดชัดเจน หรือาจกล่าวได้ว่า Time interval คือ Duration ที่มีการกำหนดจุดเริ่มต้นหรือจุดสิ้นสุดไว้ ใน ISO 8601 เราสามารถเขียน Time interval ได้หลายรูปแบบ ดังนี้

  • <start>/<end> คือกำหนดวันเวลาเริ่ม และวันเวลาสิ้นสุดลงไปตรงๆ คั่นด้วยเครื่องหมาย forward slash (/) เช่น 2007-03-01T13:00:00Z/2008-05-11T15:30:00Z

  • <start>/<duration> กำหนดวันเวลาเริ่มต้นตามด้วยเครื่องหมาย forward slash (/) และ Duration เช่น 2007-03-01T13:00:00Z/P1Y2M10DT2H30M

  • <duration>/<end> กำหนด Duration ตามด้วยเครื่องหมาย forward slash (/) และวันเวลาสิ้นสุด เช่น P1Y2M10DT2H30M/2008-05-11T15:30:00Z

  • <duration> ใส่แค่ Duration อย่างเดียวเลย จะใช้ได้ก็ต่อเมื่ออยู่ในบริบท (context) ที่เหมาะสม

References

Calendar date - Wikipedia

ISO 8601 - Wikipedia

#‎day58 #365วันแห่งโปรแกรม ‪#‎โครงการ365วันแห่ง‬...