บทความ:
Perl
PHP
HTML
CSS
XML
DTD
XSD
RSS
WSDL
Linux
Site Map
Board

Expression รูปแบบการค้นหาคำ

นนทชัย ทรัพย์ทวีพงศ์ 2009-08-02 19:34:52  ให้คะแนนบทความนี้(0)  ลดคะแนนบทความ(0)  จำนวน Comment(0)  จำนวนคนอ่าน(497)  

ในการกำหนดรูปแบบการค้นหาคำ (Expression) ของภาษา Perl นั้นมีลักษณะเช่นเดียวกับ Linux

เพราะเนื่องจากภาษา Perl เป็นภาษาที่จัดการเกี่ยวกับระบบ Linux จึงทำให้การกำหนด expression มีลักษณะเหมือนกัน (ตามที่ได้กล่าวในบทความก่อน) ซึ่งรายละเอียดการกำหนด expression ในการค้นหาคำนั้นจะค่อย ๆ กล่าวไปที่ละลำดับเพื่อให้ผู้อ่านไม่งง และเข้าใจง่าย

แบบแรกจะเรียกว่า Simple Matching

ซึ่งเป็นแบบที่กำหนดง่ายสุด นั่นก็คือการกำหนดคำที่ต้องการค้นหาแบบตรงตัว ดังตัวอย่าง

$user_location = "I see thirteen black cat under a ladder.";
if ($user_location =~ /thirteen/) {
     print "Eek, bad luck!\n";
}
# =~ /thirteen/ แปลว่า ในตัวแปร $user_location ต้องมีคำว่า thirteen อยู่ที่ไหนก็ได้ในนั้น
# ถ้ามี = true ไม่มี = false

การกำหนดแบบ Metacharacters

การกำหนดแบบ Metacharacters พูดแบบเข้าใจง่าย ๆ ก็คือกำหนดถึงคำที่เริ่มต้น (^) กับคำที่สิ้นสุด ($) ของบรรทัดที่ค้นหานั้น ๆ

# ^     ->     สตริงที่ต่อจาก ^ จะต้องมีในจุดเริ่มต้นของ String ที่ค้นหา
# $     ->     สตริงที่อยู่ก่อน $ จะต้องมีในจุดสุดท้ายของ String ที่ค้นหา
# เช่น
for $line() {
     # if the line starts with http: and end with html
     if (($line =~ /^http:/) and ($line =~ /html$/)) {
          print $line;
     }
}

การค้นหาคำที่ละเอียดกว่าเดิม

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

# /a.b/
# คือค้นหาคำว่า a โดย . ที่คั่นกลางจะแทนด้วยตัวอักขระอะไรก็ได้ที่อยู่ในบรรทัดเดียวกัน
# แต่ต้องลงท้ายด้วย b และไม่จำเป็นต้องอยู่ท้ายประโยค
# เช่น acdeb, acb, acgbz เป็นต้น
# ถ้าต้องการให้ค้นหาอักขระ . ด้วยให้ใช้ /Mr\./ จะใช้ /Mr./ไม่ได้

นอกจากนี้ยังมีสัญลักษณ์อีก 3 ตัวที่เป็นตัวช่วยในการค้นหาคำ ซึ่งมีความหมายในการใช้ต่างกันเพียงนิดเดียว ดังนี้

# +  ->  /ab+c/ คือในประโยคนั้น ๆ จะต้องมีอักขระข้างหน้า + อย่างน้อย 1 ตัวและมีกี่ตัวก็ได้ เช่น abc, abbc, abbbbc
# *  ->  /ab*c/ จะมีการใช้เหมือนกับ + เพียงแต่จะต่างกันตรงที่ไม่มีอักขระข้างหน้า * ก็ได้ เช่น ac, abc, abbc  คือจะต้องมีอักขระข้างหน้า * อย่างน้อย 0 ตัวและมีกี่ตัวก็ได้
# ? ->  /ab?c/ อักขระข้างหน้า ? จะไม่มีก็ได้หรือถ้ามี จะต้องมีแค่ 1 ตัว เช่น ac, abc

เมื่อเรารู้จักสัญลักษณ์เพิ่มเติมเรียบร้อยแล้ว เราสามารถย่อคำสั่งค้นหาคำได้สั้นลงดังนี้

for $line (<URLLIST>) {
     if ($line =~ /^http:.+html$/) {
          print $line;
     }
}
# หมายความว่า เริ่มบรรทัดจะต้องมีคำว่า http:
# และต่อจากนั้นต้องมีอักขระอะไรก็ได้อย่างน้อย 1 ตัว
# และต้องลงท้ายสตริงด้วย html

Character Classes

ความหมายของ Character Classes แต่ละตัวมีความหมายแตกต่างกันไป เราลองไปดูความหมายของ Character Class เพื่อสามารถนำไปใช้ในการค้นหาคำที่ละเอียดยิ่งขึ้น

\d  ->  ตัวเลขตัวเดียว
\w  ->  ตัวอักษร ตัวเลข หรือ _ เพียงตัวเดียว
\s  ->  ช่องว่าง หรือแท็บ (\n, \r)
\D  ->  inverse ของ \d นั่นคือ อะไรก็ได้ที่ไม่ใช่ตัวเลข
\W  ->  inverse ของ \w นั่นคือ อะไรก็ได้ที่ไม่ใช่ letter, digit, underscored
\S  ->  inverse ของ \s นั่นคือ อะไรก็ได้ที่ไม่ใช่ whitespace, tab (\n, \r)
# เช่นการเช็คหมายเลขโทรศัพท์ของ USA จะมีรูปแบบ 555-1212
unless ($phone =~ /\d\d\d-\d\d\d\d/) {
     print "That's not a phone number.";
}
# หรือ
unless($phone =~ /\d{3}-\d{4}/) {
     print "That's not a phone number.";
}

เรายังสามารถกำหนด Character Classes เองได้ ซึ่งต้องอยู่ภายใน [] เช่น

# [aeiou]
# /b[aeiou]g/ จะ match กับ bag, beg, big, bog, bug
# และยังสามารถใช้ - เพื่อกำหนดช่วงของอักขระได้เช่น
# [a-u] ซึ่งหมายความว่าตัวอักษรตั้งแต่ a - u
# \d มีความหมายเท่ากับ  [0-9]
# เช่นการค้นหาสระ aeiou อะไรก็ได้ (จะเป็น a|e|i|o|u ก็ได้) ที่ต้องมีอย่างน้อย 2 ตัว
if ($string =~ /[aeiou]{2}/) {
     print "The string contains at least two vowels in a rows\n";
}

เราสามารถ invert Character classes เหล่านี้ได้โดยใส่ ^ ไว้ข้างหน้าอักขระเหล่านั้น เช่น [^aeiou] เพื่อค้นหาคำที่ไม่มีอักขระ aeiou อยู่ในนั้น และต้องระมัดระวังการใช้ ^ เพราะในบทที่แล้วจะหมายถึงจุดเริ่มต้นของสตริง แต่ในบทนี้จะเป็นการ invers Character Classes

การกำหนด Flag ให้กับ regular expression

ค่าคงที่ของ regular expression คือเป็น case-sensitive (/bob/ ไม่ match กับ /Bob/) เราสามารถใส่ flag หลัง regular expression เพื่อเปลี่ยนแปลงการกระทำของมัน (จาก case-sensitive เป็น case-insensitive) โดยใช้ Flag i เช่น

$great = "Hey everybody, it's Bob and David!";
if ($great =~ /bob/i) {
     print "Hi, Bob!\n";
}
# จาก $great จะเข้าเงื่อนไขนี้ เนื่องจากใช้ flag i ที่ท้าย regular expression

จบไปอีกบทความนึง เกี่ยวกับ Expression ครับซึ่งมีประโยชน์มากในการเขียนโปรแกรม perl กับการค้นหาคำ และผมหวังว่าบทความที่ผมเขียนไปจะมีประโยชน์กับผู้อ่านทุกคนนะคร้าบบบบ......

แหล่งที่มา:

Related Article

Related Download

ไม่มีรายการดาวน์โหลด



Login  Login
ค้นหา  Search
ความเห็นของผู้อ่าน
ยังไม่มีความเห็นในบทความนี้
Comment