Computer >> บทช่วยสอนคอมพิวเตอร์ >  >> การเขียนโปรแกรม >> Python

Pattern Matching ใน Python ด้วย Regex


Regular Expression คืออะไร?

ในโลกความเป็นจริง การแยกวิเคราะห์สตริงในภาษาโปรแกรมส่วนใหญ่จัดการโดย Regular Expression Regular Expression ในภาษาโปรแกรม Python เป็นวิธีที่ใช้สำหรับจับคู่รูปแบบข้อความ

โมดูล "re" ซึ่งมาพร้อมกับการติดตั้ง Python ทุกครั้งให้การสนับสนุน Regular Expression

ใน Python การค้นหา Regular Expression มักเขียนเป็น:

match = re.search(pattern, string)

เมธอด re.search() รับสองอาร์กิวเมนต์ คือ รูปแบบ Regular Expression และสตริง และค้นหารูปแบบนั้นภายในสตริง หากพบรูปแบบภายในสตริง search() จะคืนค่า match object หรือ None หากไม่พบ ดังนั้นใน Regular Expression กำหนดสตริงหนึ่ง ให้กำหนดว่าสตริงนั้นตรงกับรูปแบบที่กำหนดหรือไม่ และอาจรวบรวม substring ที่มีข้อมูลที่เกี่ยวข้องได้ Regular Expression สามารถใช้ตอบคำถามได้ เช่น −

  • สตริงนี้เป็น URL ที่ถูกต้องหรือไม่?

  • ผู้ใช้ใดใน /etc/passwd อยู่ในกลุ่มที่กำหนด?

  • วันที่และเวลาของข้อความเตือนทั้งหมดในไฟล์ log คืออะไร?

  • ชื่อผู้ใช้และเอกสารที่ร้องขอโดย URL ที่ผู้เยี่ยมชมพิมพ์คืออะไร?

การจับคู่รูปแบบ (Matching patterns)

Regular Expressions เป็นภาษาย่อยที่ซับซ้อน พวกมันอาศัยตัวอักษรพิเศษในการจับคู่สตริงที่ไม่รู้จัก แต่ลองเริ่มจากตัวอักษรตัวจริง เช่น ตัวอักษร ตัวเลข และตัวอักษรเว้นวรรค ซึ่งจับคู่กับตัวเองเสมอ มาดูตัวอย่างพื้นฐาน:

# ต้องการโมดูล 're' สำหรับ regular expression import re # search_string = "TutorialsPoint" pattern = "Tutorials" match = re.match(pattern, search_string) # If-statement หลังจาก search() ทดสอบว่าสำเร็จหรือไม่ if match:     print("regex matches: ", match.group()) else:     print('pattern not found')

ผลลัพธ์

regex matches: Tutorials

การจับคู่สตริง (Matching a string)

โมดูล "re" ของ Python มีเมธอดมากมาย และเพื่อทดสอบว่า Regular Expression เฉพาะตัวตรงกับสตริงเฉพาะตัวหรือไม่ คุณสามารถใช้ re.search() ได้ อ็อบเจกต์ re.MatchObject ให้ข้อมูลเพิ่มเติม เช่น ส่วนใดของสตริงที่พบการจับคู่

ไวยากรณ์

matchObject = re.search(pattern, input_string, flags=0)

ตัวอย่าง

# ต้องการโมดูล 're' สำหรับ regular expression import re # ใช้ regular expression จับคู่สตริงวันที่ regex = r"([a-zA-Z]+) (\d+)" if re.search(regex, "Jan 2"):     match = re.search(regex, "Jan 2")     # จะพิมพ์ [0, 5) เนื่องจากจับคู่ที่ต้นและท้ายของ     # สตริง     print("Match at index %s, %s" % (match.start(), match.end()))     # กลุ่มมีค่าที่จับคู่ได้ โดยเฉพาะ:     # match.group(0) คืนค่าสตริงที่จับคู่เต็มรูปแบบเสมอ     # match.group(1), match.group(2), ... จะคืนค่า     # capture groups ตามลำดับจากซ้ายไปขวาในสตริงอินพุท     # match.group() เทียบเท่า match.group(0)     # ดังนั้นจะพิมพ์ "Jan 2"     print("Full match: %s" % (match.group(0)))     # ดังนั้นจะพิมพ์ "Jan"     print("Month: %s" % (match.group(1)))     # ดังนั้นจะพิมพ์ "2"     print("Day: %s" % (match.group(2))) else:     # หาก re.search() ไม่จับคู่ จะคืนค่า None     print("Pattern not Found! ")

ผลลัพธ์

Match at index 0, 5 Full match: Jan 2 Month: Jan Day: 2

เนื่องจากเมธอดข้างต้นหยุดหลังการจับคู่ครั้งแรก จึงเหมาะสำหรับการทดสอบ Regular Expression มากกว่าการแยกข้อมูล

Capturing Groups (กลุ่มการจับคู่)

หากรูปแบบมีวงเล็บสองคู่ขึ้นไป ผลลัพธ์สุดท้ายจะเป็น tuple แทนที่จะเป็นลิสต์ของสตริง ด้วยกลไกกลุ่มของวงเล็บ () และ finall() แต่ละรูปแบบที่จับคู่ได้แสดงด้วย tuple และแต่ละ tuple มี group(1), group(2).. data

import re regex = r'([\w\.-]+)@([\w\.-]+)' str = ('hello john@hotmail.com, hello@Tutorialspoint.com, hello python@gmail.com') matches = re.findall(regex, str) print(matches) for tuple in matches:     print("Username: ",tuple[0]) #username     print("Host: ",tuple[1]) #host

ผลลัพธ์

[('john', 'hotmail.com'), ('hello', 'Tutorialspoint.com'), ('python', 'gmail.com')] Username: john Host: hotmail.com Username: hello Host: Tutorialspoint.com Username: python Host: gmail.com

การค้นหาและแทนที่สตริง (Finding and replacing string)

งานทั่วไปอีกอย่างคือค้นหาทุกครั้งของรูปแบบในสตริงที่กำหนดและแทนที่พวกมัน re.sub(pattern, replacement, string) จะทำได้พอดี ตัวอย่างเช่น เพื่อแทนที่โดเมนอีเมลเก่าทั้งหมด

โค้ด

# requid library import re #given string str = ('hello john@hotmail.com, hello@Tutorialspoint.com, hello python@gmail.com, Hello World!') #pattern to match pattern = r'([\w\.-]+)@([\w\.-]+)' #replace the matched pattern from string with, replace = r'\1@XYZ.com'     ## re.sub(pat, replacement, str) -- returns new string with all replacements,     ## \1 is group(1), \2 group(2) in the replacement print (re.sub(pattern, replace, str))

ผลลัพธ์

hello john@XYZ.com, hello@XYZ.com, hello python@XYZ.com, Hello World!

Re options flags (ตัวเลือก flag ของ re)

ใน Python Regular Expression เช่นข้างต้น เราสามารถใช้ตัวเลือกต่างๆ เพื่อปรับเปลี่ยนพฤติกรรมของการจับคู่รูปแบบ อาร์กิวเมนต์เพิ่มเติมเหล่านี้ flag ทางเลือกถูกเพิ่มเข้าไปในฟังก์ชัน search() หรือ findall() เป็นต้น เช่น re.search(pattern, string, re.IGNORECASE)

  • IGNORECASE −

    ตามที่ชื่อบ่งชี้ ทำให้รูปแบบไม่สนใจตัวพิมพ์เล็ก/ใหญ่ (upper/lowercase) ด้วยนี้ สตริงที่มี 'a' และ 'A' จะจับคู่ทั้งคู่

  • DOTALL

    re.DOTALL อนุญาตให้ dot(.) metacharacter จับคู่ตัวอักษรทั้งหมดรวมถึง newline (\n)

  • MULTILINE

    re.MULTILINE อนุญาตให้จับคู่จุดเริ่มต้น(^) และจุดสิ้นสุด($) ของแต่ละบรรทัดของสตริง แต่โดยปกติ ^ และ & จะจับคู่แค่จุดเริ่มต้นและจุดสิ้นสุดของสตริงทั้งหมด