φυβλαςのβλογ
บล็อกของ phyblas



ความแตกต่างระหว่าง python 2.x และ 3.x
เขียนเมื่อ 2015/12/17 19:00
แก้ไขล่าสุด 2021/09/28 16:42
ตั้งแต่ไพธอน 3 ถูกปล่อยออกมาในปี 2008 ก็มีเสียงวิพากย์วิจารณ์มากมายว่ามีความแตกต่างไปจากไพธอน 2 มากเกินไปจนทำให้สูญเสียความเข้ากันได้

โค้ดที่เขียนด้วยไพธอน 2 ไม่สามารถนำมาใช้ในไพธอน 3 ได้โดยไม่มีการปรับแก้ ด้วยเหตุนี้จึงมีคนมากมายยังคงนิยมใช้ไพธอน 2 ต่อไปโดยไม่เคยคิดจะเปลี่ยนมาใช้ไพธอน 3

แม้ว่าคนที่เพิ่งมาศึกษาภาษาไพธอนเอาช่วงหลังๆมานี้มักจะได้รับคำแนะนำให้ศึกษาไพธอน 3 มากกว่า แต่ถึงอย่างนั้นไพธอน 2 ก็ยังเป็นที่นิยมมากกว่าอยู่ ดังนั้นจึงจำเป็นต้องเรียนรู้ไว้บ้าง

หากทำความเข้าใจเรื่องความแตกต่างระหว่างไพธอน 2 และ 3 ได้แล้ว ไม่ว่าจะเริ่มศึกษาจากเวอร์ชันไหนก็สามารถเปลี่ยนไปใช้อีกเวอร์ชันได้ไม่ยากเย็น

- การตั้งชื่อตัวแปร
- ชนิดข้อมูลจำนวนเต็ม
- การใช้เลขนอกเหนือจากเลขฮินดูอารบิกเป็นค่าตัวเลข
- ฟังก์ชัน print
- ฟังก์ชัน input
- การหารจำนวนเต็ม
- การยกกำลังจำนวนติดลบ
- ชนิดข้อมูลของสายอักขระ
- ชนิดข้อมูลของ range
- การจัดการกับตัวแปรที่ใช้ใน for
- เมธอด keys, values และ items ของดิกชันนารี
- ฟังก์ชัน map, filter และ zip
- การใช้ฟังก์ชัน super
- ออบเจ็กต์ของความผิดพลาดในโครงสร้าง try except
- เมธอด next กับ __next__
- มอดูล __future__



การตั้งชื่อตัวแปร
ในไพธอน 2 ชื่อตัวแปรจะใช้ได้แค่อักษรโรมัน ๒๖ ตัวหลัก (ทั้งพิมพ์ใหญ่และพิมพ์เล็ก) และตัวเลข 0 ถึง 9 แล้วก็สัญลักษณ์ขีดล่าง _

แต่ในไพธอน 3 สามารถตั้งชื่อเป็นอักษรชนิดอื่นได้ เช่น
- อักษรโรมันที่มีสัญลักษณ์เพิ่มเติม (áéíóúýäëïöüÿøåæñ ฯลฯ)
- อักษรกรีก (αβγδεζηθικλμνξοπρστυφχψω ฯลฯ)
- อักษรไทย ลาว เขมร เวียดนาม จีน ญี่ปุ่น เกาหลี ฯลฯ (ไทย ລາວ ខ្មែរ Việt 漢字 カタカナ ひらがな 한글 ฯลฯ)
- และอื่นๆอีกมากมาย

การที่สามารถตั้งชื่อตัวแปรได้หลากหลายขึ้นก็อาจช่วยให้การใช้งานยืดหยุ่นขึ้นได้ดี

ตัวอย่าง ลองพิมพ์
จำนวนจังหวัดทั้งหมดในประเทศไทย = 77

ในไพธอน 3 จะไม่มีอะไรเกิดขึ้น ข้อความยาวๆนี้ได้รับการยอมรับให้เป็นชื่อตัวแปร และเก็บค่าตัวเลขไปเรียบร้อย แต่ในไพธอน 2 จะขึ้นว่า
SyntaxError: invalid syntax



ชนิดข้อมูลจำนวนเต็ม
ในไพธอน 2 นั้นจำนวนเต็มถูกแบ่งเป็น ๒ ชนิดคือ int กับ long แต่ในไพธอน 3 ได้รวมกันเป็นชนิดเดียวคือ int
โดยค่า int จะมีขอบเขตจำกัดอยู่ค่าหนึ่ง

ค่าสูงสุดของ int นั้นมีจำกัดอยู่แล้วแต่เครื่องโดยอาจจะเป็น 2 ยกกำลัง 63 ลบ 1 หรือ 2 ยกกำลัง 31 ลบ 1

ลองพิมพ์
import sys
print(sys.maxint)
ก็จะได้ค่าสูงสุดของ int ออกมา

ลองพิมพ์ลงในเชลโต้ตอบไปตามนี้
2**80
ในไพธอน 3 จะได้ผลลัพธ์เป็น
1208925819614629174706176

แต่ในไพธอน 2 จะได้ผลลัพธ์เป็น
1208925819614629174706176L

สิ่งที่ต่างกันคือในไพธอน 2 มีตัว L โผล่เพิ่มขึ้นมา ซึ่งตัว L ในที่นี้เป็นตัวบ่งบอกว่าเป็นข้อมูลชนิด long นั่นเอง

หมายความว่าในไพธอน 2 ถ้าหากใส่เลขที่ใหญ่เกินขอบเขตที่จะเป็น int ได้ก็จะถูกเก็บในรูปของ long

ในขณะที่ในไพธอน 3 จะใหญ่แค่ไหนก็ยังเป็น int อยู่ดี และจะไม่มีข้อมูลชนิด long

ดังนั้นหากพิมพ์ 1208925819614629174706176L ลงในไพธอน 3 ก็จะขึ้นว่า
SyntaxError: invalid syntax



การใช้เลขนอกเหนือจากเลขฮินดูอารบิกเป็นค่าตัวเลข
ในไพธอน 2 นั้นหากจะแปลงสายอักขระที่เก็บตัวเลขให้เป็นข้อมูลชนิดจำนวนตัวเลขจะต้องใช้เลขฮินดูอารบิกเท่านั้น เช่น
int('12') # ได้ 12

แต่ในไพธอน 3 อาจใช้เลขไทยหรือเลขอื่นๆได้อีกหลายชนิด หรืออาจใช้ปนกันก็ได้ เช่น
int('๑๒') # ได้ 12
float('๑๒.๒') # ได้ 12.2
float('๑2.๒2') # ได้ 12.22

เพียงแต่ว่ายังไงก็จำเป็นต้องเขียนเป็นสายอักขระแล้วแปลงเป็นตัวเลขอีกที ไม่สามารถนำมาคำนวณโดยตรง เช่น
๑+๑
ได้
SyntaxError: invalid character in identifier
ต้องเขียนเป็น
int('๑')+int('๑') # ได้ 2

นอกจากเลขไทยแล้วยังใช้ตัวเลขของภาษาอื่นได้อีกหลายชนิด เช่น ลาว เขมร พม่า เพียงแต่ว่าเลขจีนไม่สามารถใช้ได้
นี่ก็ถือเป็นรายละเอียดปลีกย่อยเล็กๆอย่างหนึ่งที่ถูกเพิ่มเข้ามา



ฟังก์ชัน print
เรื่องการใช้คำสั่ง print นี้เป็นตัวอย่างหนึ่งของความเปลี่ยนแปลงที่ถูกยกมาพูดถึงบ่อยที่สุด

เดิมทีในไพธอน 2 คำสั่ง print มีโครงสร้างการใช้แบบนี้
print 'sawatdi'

นั่นคือ print แล้วเว้นวรรค ตามด้วยสิ่งที่ต้องการแสดงผลออกมา

แต่ว่าในไพธอน 3 ได้ถูกเปลี่ยนกลายเป็นแบบนี้
print('sawatdi')

ก็คือจำเป็นที่นะต้องใส่วงเล็บครอบสิ่งที่ต้องการแสดงผลออกมา หากไม่ใส่ก็จะขัดข้องไม่สามารถรันได้

อัน ที่จริงความเปลี่ยนแปลงนี้มีความหมายมากถึงระดับโครงสราง เพราะในไพธอน 2 print ถือว่าเป็นแค่คำสั่งหนึ่ง ไม่ใช่ฟังก์ชัน จึงมีรูปแบบการทำงานคล้ายกับ for หรือ while คือใช้การจัดวางโดยอาจจะเว้นวรรคหรือใส่วงเล็บก็ได้

แต่ในไพธอน 3 ถือว่ากลายเป็นฟังก์ชันไปโดยสมบูรณ์ เมื่อเป็นฟังก์ชันก็จะต้องมีวงเล็บ ( ) และสิ่งที่ต้องการพิมพ์ก็มีสถานะเป็นอาร์กิวเมนต์ของฟังก์ชัน

หากลองพิมพ์
type(print)
ในไพธอน 3 ก็จะได้ผลลัพธ์เป็น
builtin_function_or_method

แต่หากลองพิมพ์ในไพธอน 2 จะได้
SyntaxError: invalid syntax

ดังนั้นจะเห็นได้ว่าการเปลี่ยนแปลงวิธีการเขียนนี้เกิดขึ้นจากการเปลี่ยนแปลงไวยากรณ์ของภาษา

อนึ่ง ที่จริงแล้วในในไพธอน 2 จะใส่วงเล็บก็ได้เหมือนกัน เพียงแต่ว่าหากมีจุลภาค , อยู่ในข้อความจะให้ผลที่แตกต่างจากไพธอน 3

ลองเปรียบเทียบ

print('nǐhǎo','konnichiwa')
ในไพธอน 3 ได้ผลเป็น
nǐhǎo konnichiwa

ส่วนในไพธอน 2 ได้ผลเป็น
('n\xc7\x90h\xc7\x8eo', 'konnichiwa')
นั่นคือผลออกมาเป็นทูเพิล แทนที่จะเป็นข้อความต่อกัน จะเห็นได้ว่าการใส่วงเล็บถูกตีความไปต่างกัน

แน่นอนว่าเมื่อใส่วงเล็บแล้วได้ทูเพิล หากลองใส่เป็นวงเล็บเหลี่ยมเช่น
print['nǐhǎo','konnichiwa']
ผลที่ได้ก็จะกลายเป็นลิสต์

ในขณะที่ถ้าต้องการให้แสดงผลเหมือนกับในไพธอน 3 ก็จะต้องไม่ใส่วงเล็บ นั่นคือ
print'nǐhǎo','konnichiwa'

อย่างไร ก็ตาม ความเปลี่ยนแปลงนี้เกิดขึ้นที่คำสั่ง print แต่สำหรับ if และ while ไม่มีอะไรเปลี่ยนแปลง ยังคงสามารถใส่หรือไม่ใส่วงเล็บก็ได้

อีกเรื่องหนึ่งคือการพิมพ์เพื่อให้ขึ้นบรรทัดต่อ ถ้าเป็นในไพธอน 3 พิมพ์เป็น
print('ความรักก็เป็นแค่ bug อย่างหนึ่ง', end='')
print('ที่เกิดขึ้นจากปฏิกิริยาทางไฟฟ้าในสมองเท่านั้น')
ได้ผลเป็น
ความรักก็เป็นแค่ bug อย่างหนึ่งที่เกิดขึ้นจากปฏิกิริยาทางไฟฟ้าในสมองเท่านั้น

แต่ในไพธอน 2 ต้องพิมพ์เป็น
print'ความรักก็เป็นแค่ bug อย่างหนึ่ง',
print'ที่เกิดขึ้นจากปฏิกิริยาทางไฟฟ้าในสมองเท่านั้น'
ได้ผลเป็น
ความรักก็เป็นแค่ bug อย่างหนึ่ง ที่เกิดขึ้นจากปฏิกิริยาทางไฟฟ้าในสมองเท่านั้น
(ที่มาของข้อความ http://hinaboshi.com/walidet/620548994630542)



ฟังก์ชัน input
ในไพธอน 2 นั้นฟังก์ชัน input จะเป็นการใส่ข้อมูลที่เป็นตัวเลข แต่หากจะใส่สายอักขระต้องเป็น raw_input

แต่ในไพธอน 3 ถูกแก้ให้ input เป็นการนำเข้าสายอักขระเท่านั้น และฟังก์ชัน raw_input ก็หายไป ไม่สามารถใช้ได้แล้ว

ยกตัวอย่าง เช่น
a = input()

แล้วลองพิมพ์ข้อความอะไรก็ได้เข้าไปโดยที่ไม่ใส่เครื่องหมายคำพูดคร่อม

ในไพธอน 3 จะไม่มีอะไรเกิดขึ้น ค่าของสายอักขระเข้าไปเก็บในตัวแปร a ตามปกติ แต่ในไพธอน 2 จะขึ้นว่า
NameError: name 'ข้อความอะไรก็ได้' is not defined

แต่ก็สามารถใส่สายอักขระได้โดยใส่เครื่องหมายคำพูดคร่อม

สรุปแล้วคือฟังก์ชัน input ในไพธอน 2 สามารถใส่ข้อมูลได้ทุกชนิด

ในขณะที่ในไพธอน 3 นั้นข้อมูลที่พิมพ์ไปจะกลายเป็นสายอักขระไปหมด แม้ว่าจะพิมพ์ตัวเลขก็ตาม

เช่นใส่ 12 ลงไปจากนั้น print(a) ถ้าเป็นไพธอน 3 จะได้เป็น '12' ออกมา คือเป็นสายอักขระที่เก็บอักษรตัวเลข 1 และ 2
ในขณะที่ถ้าเป็นไพธอน 2 จะได้เป็น 12 ซึ่งเป็นตัวเลขเลย

ในไพธอน 3 หากต้องการจะได้เป็นตัวเลขก็ต้องแปลงอีกต่อ เช่น
a = int(input())
b = float(input())

ความแตกต่างตรงนี้จำเป็นจะต้องระวังให้ดี เพราะให้ผลแตกต่างกันมากพอสมควร



การหารจำนวนเต็ม
ในไพธอน 2 นั้นจำนวนเต็มหารจำนวนเต็มจะได้จำนวนเต็มเช่นเดิม และหากเหลือเศษจะมีการปัดเศษให้เป็นจำนวนเต็ม

แต่ในไพธอน 3 จำนวนเต็มหารจำนวนเต็มจะได้จำนวนจริง ซึ่งมีทศนิยมได้ ดังนั้นจะไม่มีการปัดเศษ
ยกตัวอย่าง
print(5/3)

ในไพธอน 3 จะได้
1.6666666666666667

นั่นคือข้อมูลถูกเปลี่ยนเป็นจำนวนจริงซึ่งมีทศนิยมได้

ส่วนในไพธอน 2 จะได้
1
นั่น คือยังคงเป็นจำนวนเต็มอยู่ หารแล้วเศษจะโดนปัดทิ้งไปหมด โดยการปัดเศษนี้ไม่ใช่การปัดแบบประมาณค่า แต่เป็นการเอาเศษออกให้หมด แม้ว่าเศษนั้นจะเกิน 0.5 ก็ถูกปัดลง

นี่เป็นข้อแตกต่างสำคัญที่อาจ ต้องจำเอาไว้ เวลาที่ไปเขียนภาษาอื่นก็จะเจอทั้งภาษาที่มีการปัดและไม่มีการปัด อาจต้องจำแยก แต่หากไม่อยากวุ่นวายขอแนะนำว่าให้แปลงเป็นเลขจำนวนจริงทุกครั้งที่รู้ว่า หารแล้วอาจมีเศษ เพราะหากใช้ไพธอน 3 จนชินแล้วพอไปใช้ไพธอน 2 แล้วไปใช้ความเคยชินแบบเดิมก็จะได้ผลการคำนวณที่ผิดพลาดได้

สามารถแก้ปัญหาในไพธอน 2 ได้ไม่ยาก ด้วยการเติมจุดทศนิยมหลังจำนวนใดจำนวนหนึ่งที่ร่วมคำนวณ
5./3

เท่านี้ก็จะได้ผลเป็นจำนวนที่มีทศนิยมแล้ว



การยกกำลังจำนวนติดลบ
ในโลกของความเป็นจริงแล้วจำนวนติดลบก็สามารถยกกำลังได้ เพียงแต่จะออกมาเป็นจำนวนเชิงซ้อน

แต่ในไพธอน 2 หากจำนวนติดลบยกกำลังก็จะขัดข้องทันที ในขณะที่ในไพธอน 3 จะเปลี่ยนเป็นข้อมูลชนิดจำนวนเชิงซ้อนให้เลย เช่น
(-2)**1.1

ในไพธอน 3 ได้
(-2.0386342710747223-0.6623924280875919j)

แต่ในไพธอน 2 ได้
ValueError: negative number cannot be raised to a fractional power

ใน ไพธอน 2 จำนวนจริงไม่ถูกเปลี่ยนเป็นจำนวนเชิงซ้อนโดยอัตโนมัติ จึงจำเป็นต้องเปลี่ยนชนิดข้อมูลให้เป็นจำนวนเชิงซ้อนก่อน โดยเขียนเป็น
complex(-2)**1.1
หรือ
(-2+0j)**1.1



ชนิดข้อมูลของสายอักขระ
รายละเอียดแยกเขียนเอาไว้ใน https://phyblas.hinaboshi.com/20151219



ชนิดข้อมูลของ range
รายละเอียดแยกเขียนเอาไว้ใน https://phyblas.hinaboshi.com/20151218



การจัดการกับตัวแปรที่ใช้ใน for
ในไพธอน 3 เมื่อใช้คำสั่ง for สำหรับสร้างลิสต์ ตัวแปรนั้นจะถูกแยกออกเป็นคนละโลกกับตัวแปรภายนอก กล่าวคือต่อให้ชื่อตัวแปรซ้ำกันก็จะไม่กระทบต่อตัวแปรนั้นที่อยู่นอกคำสั่ง สร้างลิสต์ เช่น
i=10
print('ค่า i ก่อน for:', i)
print('ค่า i ใน for:', [i for i in range(5)])
print('ค่า i หลัง for:', i)
จะได้ผลลัพธ์เป็น
ค่า i ก่อน for: 10
ค่า i ใน for: [0, 1, 2, 3, 4]
ค่า i หลัง for: 10

เพราะ กรณีนี้ตัวแปร i ที่นิยามก่อนเริ่มใช้คำสั่ง for สร้างลิสต์ กับตัวแปร i ที่อยู่ในคำสั่งนั้นเป็นคนละตัวกัน ดังนั้นต่อให้สร้างลิสต์เสร็จค่า i ที่นิยามขึ้นก่อนหน้าก็ไม่มีการเปลี่ยนแปลง
แต่ถ้าเป็นในไพธอน 2 จะไม่เป็นเช่นนั้น

i=10
print 'ค่า i ก่อน for:', i
print 'ค่า i ใน for:', [i for i in range(5)]
print 'ค่า i หลัง for:', i

ผลลัพธ์
ค่า i ก่อน for: 10
ค่า i ใน for: [0, 1, 2, 3, 4]
ค่า i หลัง for: 4

เพียง แต่ว่าความเปลี่ยนแปลงนี้เกิดเฉพาะสำหรับ for ที่ใช้สร้างลิสต์เท่านั้น สำหรับการใช้ for เป็นคำสั่งวนซ้ำยังทำให้เกิดการเปลี่ยนแปลงค่าตัวแปรเช่นเดิม

ไพธอน 3
i=10
print('ค่า i ก่อน for:', i)
print('ค่า i ใน for:',end=' ')
for i in range(5): print(i,end=' ')
print('\nค่า i หลัง for:', i)
ผลลัพธ์
ค่า i ก่อน for: 10
ค่า i ใน for: 0 1 2 3 4
ค่า i หลัง for: 4

ไพธอน 2
i=10
print 'ค่า i ก่อน for:', i
print 'ค่า i ใน for:',
for i in range(5): print i,
print '\nค่า i หลัง for:', i
ผลลัพธ์
ค่า i ก่อน for:  10
ค่า i ใน for: 0 1 2 3 4
ค่า i หลัง for: 4

จะเห็นว่าไม่มีการเปลี่ยนแปลง เพราะค่าของตัวแปร i ที่เปลี่ยนไปตามการวนซ้ำถือเป็นตัวเดียวกับ i ที่นิยามก่อนหน้านั้น



เมธอด keys, values และ items ของดิกชันนารี
ในไพธอน 2 เมธอด keys, values และ items จะคืนค่าลิสต์ของคีย์, ค่า และ ทูเพิลของคีย์และค่า ตามลำดับ เช่น
dic = {'a': 5, 'b': 3, 'd': 7}
print(dic.keys())
print(dic.values())
print(dic.items())
ได้
['a', 'b', 'd']
[5, 3, 7]
[('a', 5), ('b', 3), ('d', 7)]
แต่ในไพธอน 3 จะคืนค่าของข้อมูลซึ่งเป็นตัวชี้ถึงค่าในดิกชันนารี โดยจะได้เป็นออบเจ็กต์ชนิด dict_keys, dict_values และ dict_items
dict_keys(['d', 'b', 'a'])
dict_values([7, 3, 5])
dict_items([('d', 7), ('b', 3), ('a', 5)])

ซึ่งความจริงแล้วผลนี้เทียบเท่ากับเมธอด viewkeys, viewvalues และ viewitems ในไพธอน 2
print(dic.viewkeys())
print(dic.viewvalues())
print(dic.viewitems())
ได้
dict_keys(['a', 'b', 'd'])
dict_values([5, 3, 7])
dict_items([('a', 5), ('b', 3), ('d', 7)])

แต่ในไพธอน 3 เมธอดเหล่านี้ได้หายไป ถ้าพิมพ์แบบเดียวกันในไพธอน 3 จะขึ้นว่า
AttributeError: 'dict' object has no attribute 'viewkeys'

หากต้องการให้ผลของ keys, values และ items ในไพธอน 3 เหมือนอย่างในไพธอน 2 ก็อาจทำได้โดยแปลงเป็นลิสต์ด้วยฟังก์ชัน list อีกที
print(list(dic.keys()))
print(list(dic.values()))
print(list(dic.items()))

หรืออาจไม่มีความจำเป็นต้องแปลง หากนำไปใช้เช่นใช้กับ for ก็ใช้งานได้เหมือนกับลิสต์
for s in dic.items(): print(s, end=' ')
ได้
('d', 7) ('b', 3) ('a', 5)


ฟังก์ชัน map, filter และ zip
ในไพธอน 2 นั้น ฟังก์ชัน map เมื่อใช้แล้วจะคืนค่าออกมาเป็นลิสต์ ไม่ว่าจะใส่ลิสต์หรือทูเพิลหรือเซ็ต

map(float,(1,2,3)) # ได้ [1.0, 2.0, 3.0]


แต่ในไพธอน 3 ฟังก์ชัน map จะให้ผลออกมาเป็นอิเทอเรเตอร์ ต้องนำมาแปลงเป็นลิสต์ต่ออีกทีจึงจะสามารถแสดงผลได

map(float,(1,2,3)) # ได้ <map at 0x112383710>
list(map(float,(1,2,3))) # ได้ [1.0, 2.0, 3.0]


ส่วนฟังก์ชัน filter ในไพธอน 2 จะให้ผลเป็นลิสต์ถ้าใส่ลิสต์หรือเซ็ตเข้าไป และให้ผลเป็นทูเพิลถ้าใส่เป็นทูเพิล

filter(lambda x:x%2,[1,2,3]) # ได้ [1, 3]
filter(lambda x:x%2==0,(1,2,3)) # ได้ (2,)
filter(lambda x:x<3,{1,2,3}) # ได้ [1, 2]


แต่ไพธอน 3 จะให้ผลเป็นอิเทอเรเตอร์เสมอ ไม่ว่าจะใส่อะไร ต้องมาแปลงอีกที

filter(lambda x:x<3,{1,2,3}) # ได้ <filter at 0x112383eb8>
set(filter(lambda x:x<3,{1,2,3})) # ได้ {1, 2}


ส่วนฟังก์ชัน zip ในไพธอน 2 จะให้ผลเป็นลิสต์ของทูเพิล

zip({1,2},{3,4}) # ได้ [(1, 3), (2, 4)]
zip([1,2,3],[4,5,6]) # ได้ [(1, 4), (2, 5), (3, 6)]


แต่ในไพธอน 3 จะได้ผลเป็นอิเทอเรเตอร์ทั้งหมด พอแปลงเป็นลิสต์แล้วจึงจะได้ผลเหมือนในไพธอน 2

zip({1,2},{3,4}) # ได้ <zip at 0x11239e188>
list(zip([1,2,3],[4,5,6])) # ได้ [(1, 4), (2, 5), (3, 6)]




การใช้ฟังก์ชัน super
ในไพธอน 2 เวลาที่จะประกาศเรียกใช้ฟังก์ชัน super จากในซับคลาสเพื่อเรียกซูเปอร์คลาสจะมีกฏการเขียนที่ค่อนข้างเข้มงวด

class Clara(object):
     def __init__(self,x):
         self.x = x
class ClariS(Clara):
     def __init__(self,x,y):
         super(ClariS,self).__init__(x)
         self.y = y
c = ClariS(2,3)


จะเห็นว่าตอนที่ประกาศคลาสหลักจำเป็นต้องมี (object) อยู่ด้านหลัง และในฟังก์ชัน super ต้องใส่อาร์กิวเมนต์ ๒ ตัว เป็นตัวคลาสและตัวอินสแตนซ์

แต่ในไพธอน 3 สามารถละได้ทั้งหมด จึงเขียนแค่นี้ได้

class Clara:
     def __init__(self,x):
         self.x = x
class ClariS(Clara):
     def __init__(self,x,y):
         super().__init__(x)
         self.y = y
c = ClariS(2,3)


แต่จะเขียนเต็มๆแบบไพธอน 2 ก็ไม่ผิด สามารถเขียนได้เช่นกัน



ออบเจ็กต์ของความผิดพลาดในโครงสร้าง try except
ในไพธอน 2 เวลาที่ใช้ except หากต้องการให้มีตัวแปรมารับออบเจ็กต์ของความผิดพลาดเพื่อนำไปแสดงผลหรือทำอะไรจะใช้จุลภาค , เขียนต่อจากชนิดของข้อผิดพลาดไปเลย

import math

try:

     1/0

except Exception, er:

     print(type(er))

     print(er)


ได้
<type 'exceptions.ZeroDivisionError'>
integer division or modulo by zero

แต่ในไพธอน 3 จะใช้ as แทน นอกจากนี้ก็จะเห็นว่าข้อความที่แสดงตอนมีข้อผิดพลาดก็อาจต่างกันด้วย

import math
try:
    1/0
except Exception as er:
    print(type(er))
    print(er)
ได้
<class 'ZeroDivisionError'>
division by zero



เวลาที่นิยามคลาสของอิเทอเรเตอร์นั้นภายในโครงสร้างจะต้องนิยามเมธอดที่จะให้ทำงานเมื่อเจอฟังก์ชัน next

ซึ่งเมธอดนั้นในไพธอน 2 มีชื่อว่า next เฉยๆ ดังนั้นจึงเขียนแบบนี้

class Iternap:
     def __init__(self):
         self.n = 0
     def __iter__(self):
         return self
     def next(self):
         self.n += 1
     return self.n


แต่ในไพธอน 3 เมธอดนี้จะชื่อว่า __next__ โดยมีขีดล่างคร่อมเพิ่มเข้ามา ซึ่งจะเห็นว่าถูกเปลี่ยนให้สัมพันธ์กับเมธอดตัวอื่นๆที่มีคุณสมบัติพิเศษ

class Iternap:
     def __init__(self):
         self.n = 0
     def __iter__(self):
         return self
     def __next__(self):
         self.n += 1
     return self.n


เมธอดที่ถูกเปลี่ยนชื่อมีแค่ next เท่านั้น เมธอดอื่นๆเช่น __init__ และ __iter__ นั้นมีขีดล่างคร่อมมาตั้งแต่ไพธอน 2 แล้ว



มอดูล __future__
ไพธอน 2 สามารถนำคำสั่งบางอย่างจากไพธอน 3 มาใช้ได้โดยการนำเข้ามอดูล __future__

เช่นหากต้องการทำให้ print กลายเป็นฟังก์ชันอย่างที่เป็นอยู่ในไพธอน 3
from __future__ import print_function
print 1
ได้
SyntaxError: invalid syntax

จะเห็นว่าไม่สามารถใช้เว้นช่องได้แล้ว ต้องใส่วงเล็บแบบในไพธอน 3

print(1,1,1,1)
ได้
1 1 1 1

จะเห็นว่าออกมาเป็นเลขเรียงต่อกันแทนที่จะออกมาเป็นทูเพิลอย่างที่เคยเป็น



และนอกจากนี้ก็ยังมีรายละเอียดอื่นๆอีกหลายอย่างซึ่งในที่นี้ไม่อาจกล่าวถึงได้หมด


อ้างอิง


-----------------------------------------

囧囧囧囧囧囧囧囧囧囧囧囧囧囧囧囧囧囧囧囧囧囧囧囧囧

ดูสถิติของหน้านี้

หมวดหมู่

-- คอมพิวเตอร์ >> เขียนโปรแกรม >> python

ไม่อนุญาตให้นำเนื้อหาของบทความไปลงที่อื่นโดยไม่ได้ขออนุญาตโดยเด็ดขาด หากต้องการนำบางส่วนไปลงสามารถทำได้โดยต้องไม่ใช่การก๊อปแปะแต่ให้เปลี่ยนคำพูดเป็นของตัวเอง หรือไม่ก็เขียนในลักษณะการยกข้อความอ้างอิง และไม่ว่ากรณีไหนก็ตาม ต้องให้เครดิตพร้อมใส่ลิงก์ของทุกบทความที่มีการใช้เนื้อหาเสมอ

สารบัญ

รวมคำแปลวลีเด็ดจากญี่ปุ่น
มอดูลต่างๆ
-- numpy
-- matplotlib

-- pandas
-- manim
-- opencv
-- pyqt
-- pytorch
การเรียนรู้ของเครื่อง
-- โครงข่าย
     ประสาทเทียม
ภาษา javascript
ภาษา mongol
ภาษาศาสตร์
maya
ความน่าจะเป็น
บันทึกในญี่ปุ่น
บันทึกในจีน
-- บันทึกในปักกิ่ง
-- บันทึกในฮ่องกง
-- บันทึกในมาเก๊า
บันทึกในไต้หวัน
บันทึกในยุโรปเหนือ
บันทึกในประเทศอื่นๆ
qiita
บทความอื่นๆ

บทความแบ่งตามหมวด



ติดตามอัปเดตของบล็อกได้ที่แฟนเพจ

  ค้นหาบทความ

  บทความแนะนำ

ตัวอักษรกรีกและเปรียบเทียบการใช้งานในภาษากรีกโบราณและกรีกสมัยใหม่
ที่มาของอักษรไทยและความเกี่ยวพันกับอักษรอื่นๆในตระกูลอักษรพราหมี
การสร้างแบบจำลองสามมิติเป็นไฟล์ .obj วิธีการอย่างง่ายที่ไม่ว่าใครก็ลองทำได้ทันที
รวมรายชื่อนักร้องเพลงกวางตุ้ง
ภาษาจีนแบ่งเป็นสำเนียงอะไรบ้าง มีความแตกต่างกันมากแค่ไหน
ทำความเข้าใจระบอบประชาธิปไตยจากประวัติศาสตร์ความเป็นมา
เรียนรู้วิธีการใช้ regular expression (regex)
การใช้ unix shell เบื้องต้น ใน linux และ mac
g ในภาษาญี่ปุ่นออกเสียง "ก" หรือ "ง" กันแน่
ทำความรู้จักกับปัญญาประดิษฐ์และการเรียนรู้ของเครื่อง
ค้นพบระบบดาวเคราะห์ ๘ ดวง เบื้องหลังความสำเร็จคือปัญญาประดิษฐ์ (AI)
หอดูดาวโบราณปักกิ่ง ตอนที่ ๑: แท่นสังเกตการณ์และสวนดอกไม้
พิพิธภัณฑ์สถาปัตยกรรมโบราณปักกิ่ง
เที่ยวเมืองตานตง ล่องเรือในน่านน้ำเกาหลีเหนือ
ตระเวนเที่ยวตามรอยฉากของอนิเมะในญี่ปุ่น
เที่ยวชมหอดูดาวที่ฐานสังเกตการณ์ซิงหลง
ทำไมจึงไม่ควรเขียนวรรณยุกต์เวลาทับศัพท์ภาษาต่างประเทศ

บทความแต่ละเดือน

2024年

1月 2月 3月 4月
5月 6月 7月 8月
9月 10月 11月 12月

2023年

1月 2月 3月 4月
5月 6月 7月 8月
9月 10月 11月 12月

2022年

1月 2月 3月 4月
5月 6月 7月 8月
9月 10月 11月 12月

2021年

1月 2月 3月 4月
5月 6月 7月 8月
9月 10月 11月 12月

2020年

1月 2月 3月 4月
5月 6月 7月 8月
9月 10月 11月 12月

ค้นบทความเก่ากว่านั้น

ไทย

日本語

中文