เหตุใดนิพจน์ทั่วไปจึงแย้งกัน [ปิด]


212

เมื่อสำรวจนิพจน์ทั่วไป (หรือที่รู้จักกันในชื่อ RegEx-es) มีบุคคลหลายคนที่ดูเหมือนจะเห็นนิพจน์ทั่วไปเป็นโฮลี่เกรล บางสิ่งที่ดูซับซ้อนมาก - ต้องเป็นคำตอบสำหรับคำถามใด ๆ พวกเขามักจะคิดว่าทุกปัญหาสามารถแก้ไขได้โดยใช้นิพจน์ทั่วไป

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

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


9
ถ้านี่คือการอภิปรายก็ไม่ควรจะปิด? แต่ฉันเห็นคำถามจริงในนั้นดังนั้นอาจไม่มีแท็กการสนทนาหรือไม่
RCIX

6
ไม่ได้ล้อเล่น. คุณนำมันขึ้นมาและผู้คนเริ่มคลั่งไคล้ที่นี่
Ryan Florence

1
การสังเกตที่ดีและการใช้ถ้อยคำในคำถาม!
imz - Ivan Zakharyaschev


คำถามคือความคิดเห็นตามกฎควรใช้ที่นี่เช่นกัน (หรือคำถามควรแก้ไขเพื่อกำหนดเป้าหมายคำตอบที่แม่นยำ) ที่กล่าวว่าฉันคิดว่า regex controverse มาจากความไม่แม่นยำของบทเรียนและคู่มือเกี่ยวกับมัน เวลาส่วนใหญ่หากไม่ได้รับข้อมูลทั้งหมดจะถูกผสมและนอกจากนี้เราจะไม่ได้รับคุณสมบัติทั้งหมด เพิ่มไปยังการใช้ภาษาพลาดคุณจบลงด้วยการเรียนรู้สิ่งที่จะสังเกตเห็นว่ามันอาจหมายถึงอย่างอื่น และในที่สุดอักขระพิเศษ regex ไม่ จำกัด เพียงหนึ่งความหมายซึ่งเพิ่มความสับสนมากขึ้น
intika

คำตอบ:


136

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


2
และใช่ regexes สามารถช้ามากอย่างยิ่งเมื่อเทียบกับการใช้ฟังก์ชั่นที่เรียบง่าย และไม่เพียง แต่ช้า แต่ประสิทธิภาพของเอ็นจิ้น regex นั้นไม่สามารถคาดเดาได้ทั้งหมดเมื่อเผชิญกับอินพุต (ผู้ใช้จัดหา) ตามอำเภอใจ
Pacerier

1
ถ้าคุณรู้ว่า regex ทำงานอย่างไรมันก็ไม่ใช่ปัญหาเลย
Shiplu Mokaddim

8
@pacerier ก็ไม่ได้รูปแบบช้าก็เครื่องยนต์ช้า ส่วนใหญ่ (ปัจจุบัน) การแสดงออกปกติเครื่องมือไม่เหมาะสมสำหรับรูปแบบที่ซับซ้อน (เช่นจำนวนมาก|หรือ.*) เพราะพวกเขาใช้เครื่องสแต็คและย้อนรอย นั่นเป็นเหตุผลที่คุณต้องปรับการแสดงผลปกติของคุณใน Perl, Java, Python, Ruby ... เอ็นจิ้นนิพจน์ปกติแบบเก่า ( grepตัวอย่างเช่น) ก่อนอื่นรวบรวมรูปแบบเป็น DFA หลังจากนั้นความซับซ้อนของรูปแบบไม่เกี่ยวข้องส่วนใหญ่ ฉันเพิ่งใช้ Java และ grep สำหรับข้อความและรูปแบบเดียวกัน: 22 นาทีกับ 2 วินาที นี่คือวิทยาศาสตร์: swtch.com/~rsc/regexp/regexp1.html
hagello

122

ทำให้ Regexes รักษาได้

ความก้าวหน้าที่สำคัญไปสู่ ​​demystify รูปแบบที่ก่อนหน้านี้เรียกว่า "การแสดงออกปกติ" คือ/xธง regex ของ Perl - บางครั้งเขียน(?x)เมื่อฝัง - ที่ช่วยให้ช่องว่าง (ทำลายบรรทัดเยื้อง) และความคิดเห็น สิ่งนี้ช่วยปรับปรุงความสามารถในการอ่านอย่างจริงจังและดังนั้นจึงสามารถบำรุงรักษาได้ พื้นที่สีขาวอนุญาตให้มีการรับรู้การรับรู้ดังนั้นคุณสามารถเห็นกลุ่มที่มีอะไร

รูปแบบที่ทันสมัยในขณะนี้ยังรองรับทั้ง backreferences ที่มีหมายเลขและชื่อตอนนี้ นั่นหมายความว่าคุณไม่จำเป็นต้องนับกลุ่มการจับกุมเพื่อหาว่าคุณต้องการ$4หรือ\7ไม่ สิ่งนี้จะช่วยเมื่อสร้างรูปแบบที่สามารถรวมอยู่ในรูปแบบเพิ่มเติม

นี่คือตัวอย่างของกลุ่มการจับภาพที่มีหมายเลขค่อนข้าง:

$ dupword = qr {\ b (?: (\ w +) (?: \ s + \ g {-1}) +) \ b} xi;
$ ที่ยกมา = qr {(["']) $ dupword \ 1} x;

และนี่คือตัวอย่างของวิธีการที่เหนือกว่าของการบันทึกชื่อ:

$dupword = qr{ \b (?: (?<word> \w+ ) (?: \s+ \k<word> )+ ) \b }xi;
$quoted  = qr{ (?<quote> ["'] ) $dupword  \g{quote} }x;

Regexes ไวยากรณ์

เหนือสิ่งอื่นใดการจับภาพที่มีชื่อเหล่านี้สามารถวางไว้ใน(?(DEFINE)...)บล็อกเพื่อให้คุณสามารถแยกการประกาศออกจากการดำเนินการตามองค์ประกอบแต่ละรายการที่มีชื่อของรูปแบบของคุณ สิ่งนี้ทำให้พวกเขาทำหน้าที่เหมือนรูทีนย่อยภายในรูปแบบ
ตัวอย่างที่ดีของ“ ไวยากรณ์ไวยากรณ์” ประเภทนี้สามารถพบได้ในคำตอบนี้และหนึ่งในนี้ สิ่งเหล่านี้มีลักษณะเหมือนประกาศทางไวยากรณ์

ตามหลังเตือนให้คุณ:

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

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

นี่เป็นอีกตัวอย่างหนึ่งของรูปแบบทางไวยากรณ์ที่ทันสมัยรูปแบบนี้สำหรับการวิเคราะห์คำ RFC 5322: use 5.10.0;

$rfc5322 = qr{

   (?(DEFINE)

     (?<address>         (?&mailbox) | (?&group))
     (?<mailbox>         (?&name_addr) | (?&addr_spec))
     (?<name_addr>       (?&display_name)? (?&angle_addr))
     (?<angle_addr>      (?&CFWS)? < (?&addr_spec) > (?&CFWS)?)
     (?<group>           (?&display_name) : (?:(?&mailbox_list) | (?&CFWS))? ; (?&CFWS)?)
     (?<display_name>    (?&phrase))
     (?<mailbox_list>    (?&mailbox) (?: , (?&mailbox))*)

     (?<addr_spec>       (?&local_part) \@ (?&domain))
     (?<local_part>      (?&dot_atom) | (?&quoted_string))
     (?<domain>          (?&dot_atom) | (?&domain_literal))
     (?<domain_literal>  (?&CFWS)? \[ (?: (?&FWS)? (?&dcontent))* (?&FWS)?
                                   \] (?&CFWS)?)
     (?<dcontent>        (?&dtext) | (?&quoted_pair))
     (?<dtext>           (?&NO_WS_CTL) | [\x21-\x5a\x5e-\x7e])

     (?<atext>           (?&ALPHA) | (?&DIGIT) | [!#\$%&'*+-/=?^_`{|}~])
     (?<atom>            (?&CFWS)? (?&atext)+ (?&CFWS)?)
     (?<dot_atom>        (?&CFWS)? (?&dot_atom_text) (?&CFWS)?)
     (?<dot_atom_text>   (?&atext)+ (?: \. (?&atext)+)*)

     (?<text>            [\x01-\x09\x0b\x0c\x0e-\x7f])
     (?<quoted_pair>     \\ (?&text))

     (?<qtext>           (?&NO_WS_CTL) | [\x21\x23-\x5b\x5d-\x7e])
     (?<qcontent>        (?&qtext) | (?&quoted_pair))
     (?<quoted_string>   (?&CFWS)? (?&DQUOTE) (?:(?&FWS)? (?&qcontent))*
                          (?&FWS)? (?&DQUOTE) (?&CFWS)?)

     (?<word>            (?&atom) | (?&quoted_string))
     (?<phrase>          (?&word)+)

     # Folding white space
     (?<FWS>             (?: (?&WSP)* (?&CRLF))? (?&WSP)+)
     (?<ctext>           (?&NO_WS_CTL) | [\x21-\x27\x2a-\x5b\x5d-\x7e])
     (?<ccontent>        (?&ctext) | (?&quoted_pair) | (?&comment))
     (?<comment>         \( (?: (?&FWS)? (?&ccontent))* (?&FWS)? \) )
     (?<CFWS>            (?: (?&FWS)? (?&comment))*
                         (?: (?:(?&FWS)? (?&comment)) | (?&FWS)))

     # No whitespace control
     (?<NO_WS_CTL>       [\x01-\x08\x0b\x0c\x0e-\x1f\x7f])

     (?<ALPHA>           [A-Za-z])
     (?<DIGIT>           [0-9])
     (?<CRLF>            \x0d \x0a)
     (?<DQUOTE>          ")
     (?<WSP>             [\x20\x09])
   )

   (?&address)

}x;

มันไม่น่าทึ่ง - และยอดเยี่ยมใช่ไหม คุณสามารถใช้ไวยากรณ์แบบ BNF และแปลเป็นรหัสโดยตรงโดยไม่สูญเสียโครงสร้างพื้นฐาน!

หากรูปแบบทางไวยากรณ์ที่ทันสมัยยังไม่เพียงพอสำหรับคุณโมดูลที่ยอดเยี่ยมของ Damian Conway Regexp::Grammarsจะเสนอไวยากรณ์ที่สะอาดยิ่งขึ้นพร้อมกับการดีบักที่เหนือกว่าเช่นกัน นี่คือรหัสเดียวกันสำหรับการวิเคราะห์คำ RFC 5322 ใหม่ในรูปแบบจากโมดูลนั้น:

#!/usr/bin/perl

use strict;
use warnings;
use 5.010;
use Data::Dumper "Dumper";

my $rfc5322 = do {
    use Regexp::Grammars;    # ...the magic is lexically scoped
    qr{

    # Keep the big stick handy, just in case...
    # <debug:on>

    # Match this...
    <address>

    # As defined by these...
    <token: address>         <mailbox> | <group>
    <token: mailbox>         <name_addr> | <addr_spec>
    <token: name_addr>       <display_name>? <angle_addr>
    <token: angle_addr>      <CFWS>? \< <addr_spec> \> <CFWS>?
    <token: group>           <display_name> : (?:<mailbox_list> | <CFWS>)? ; <CFWS>?
    <token: display_name>    <phrase>
    <token: mailbox_list>    <[mailbox]> ** (,)

    <token: addr_spec>       <local_part> \@ <domain>
    <token: local_part>      <dot_atom> | <quoted_string>
    <token: domain>          <dot_atom> | <domain_literal>
    <token: domain_literal>  <CFWS>? \[ (?: <FWS>? <[dcontent]>)* <FWS>?

    <token: dcontent>        <dtext> | <quoted_pair>
    <token: dtext>           <.NO_WS_CTL> | [\x21-\x5a\x5e-\x7e]

    <token: atext>           <.ALPHA> | <.DIGIT> | [!#\$%&'*+-/=?^_`{|}~]
    <token: atom>            <.CFWS>? <.atext>+ <.CFWS>?
    <token: dot_atom>        <.CFWS>? <.dot_atom_text> <.CFWS>?
    <token: dot_atom>        <.CFWS>? <.dot_atom_text> <.CFWS>?
    <token: dot_atom_text>   <.atext>+ (?: \. <.atext>+)*

    <token: text>            [\x01-\x09\x0b\x0c\x0e-\x7f]
    <token: quoted_pair>     \\ <.text>

    <token: qtext>           <.NO_WS_CTL> | [\x21\x23-\x5b\x5d-\x7e]
    <token: qcontent>        <.qtext> | <.quoted_pair>
    <token: quoted_string>   <.CFWS>? <.DQUOTE> (?:<.FWS>? <.qcontent>)*
                             <.FWS>? <.DQUOTE> <.CFWS>?

    <token: word>            <.atom> | <.quoted_string>
    <token: phrase>          <.word>+

    # Folding white space
    <token: FWS>             (?: <.WSP>* <.CRLF>)? <.WSP>+
    <token: ctext>           <.NO_WS_CTL> | [\x21-\x27\x2a-\x5b\x5d-\x7e]
    <token: ccontent>        <.ctext> | <.quoted_pair> | <.comment>
    <token: comment>         \( (?: <.FWS>? <.ccontent>)* <.FWS>? \)
    <token: CFWS>            (?: <.FWS>? <.comment>)*
                             (?: (?:<.FWS>? <.comment>) | <.FWS>)

    # No whitespace control
    <token: NO_WS_CTL>       [\x01-\x08\x0b\x0c\x0e-\x1f\x7f]

    <token: ALPHA>           [A-Za-z]
    <token: DIGIT>           [0-9]
    <token: CRLF>            \x0d \x0a
    <token: DQUOTE>          "
    <token: WSP>             [\x20\x09]

    }x;

};


while (my $input = <>) {
    if ($input =~ $rfc5322) {
        say Dumper \%/;       # ...the parse tree of any successful match
                              # appears in this punctuation variable
    }
}

มีจำนวนมากของสิ่งที่ดีในการเป็นperlre manpageแต่เหล่านี้ปรับปรุงอย่างมากในลักษณะการออกแบบ regex พื้นฐานโดยไม่ได้ จำกัด เพียงอย่างเดียว Perl แท้จริงpcrepattern manpageอาจจะอ่านง่ายขึ้นและครอบคลุมดินแดนเดียวกัน

รูปแบบที่ทันสมัยแทบไม่มีอะไรเหมือนกันกับสิ่งดั้งเดิมที่คุณได้รับการสอนในชั้นเรียนของคุณออโต จำกัด


9
ใช่! ใช่! ในที่สุดมีคนแสดงตัวอย่างที่ยอดเยี่ยมของวิธีที่ regexes สามารถอ่านได้ด้วยตัวปรับเปลี่ยน x ฉันไม่อยากเชื่อเลยว่ามีคนเพียงไม่กี่คนที่รู้ว่ามันมีอยู่จริง
Shabbyrobe

1
@Shabbyrobe: /xมันไม่ได้เป็นเพียง มันใช้เรกซ์ทางไวยากรณ์กับ(?&name)รูทีนย่อย regex ภายในซึ่งทำให้สิ่งนี้เปล่งประกายได้จริงๆ
tchrist

+1 คุณเรียนรู้สิ่งใหม่เสมอ ฉันไม่ทราบว่า PCRE มีเงื่อนไข "เท็จ" สำหรับการกำหนด
NikiC

5
Python มีre.VERBOSEธงเหมือนกัน
หอยทากเชิงกล

3
เพียงแค่ gunna ไปข้างหน้าและบอกว่าฉันยังคงประหลาดใจในความยาวที่ผู้คนจะไปเพื่อให้การใช้งาน regex
ตำหนิ Victoroff

68

Regexes เป็นเครื่องมือที่ยอดเยี่ยม แต่ผู้คนต่างคิดว่า "เฮ้เครื่องมือที่ยอดเยี่ยมฉันจะใช้มันเพื่อทำ X!" โดยที่ X เป็นสิ่งที่เครื่องมือที่แตกต่างจะดีกว่าสำหรับ (มักจะเป็น parser) เป็นมาตรฐานการใช้ค้อนที่คุณต้องการปัญหาไขควง


4
เพียงจำไว้ว่า parsers ที่สุด -lexical analyzers- ยังคงใช้การแสดงออกปกติจะแยกสิ่งที่พวกเขา :-)
แจสเปอร์ BEKKERS

62
การบอกว่าตัวแยกวิเคราะห์ใช้นิพจน์ทั่วไปนั้นเหมือนกับว่าตัวแยกวิเคราะห์ใช้คำสั่งมอบหมาย มันไม่มีความหมายจนกว่าคุณจะดูว่ามีการใช้งานอย่างไร
Chas Owens

24
ใช้ RegEx เมื่อ parser ดีกว่าเป็นที่น่ารำคาญ การใช้ RegEx เมื่อฟังก์ชันค้นหาหรือแทนที่สตริงมาตรฐานของภาษาใช้งานได้ (และในเวลาเชิงเส้นปกติ) จะยกโทษให้ไม่ได้
jmucchiello

1
เห็นด้วยเพราะ RegEx จะต้องมีแจ็คของการซื้อขายทั้งหมดการประมวลผลค่าใช้จ่ายมีขนาดใหญ่มาก เพียงเพราะการใช้เอนจิน RegEx ดูเหมือนง่ายไม่ได้หมายความว่าเป็นทางออกที่ดีกว่าตัวแยกวิเคราะห์ซ้ำ (เกณฑ์ขึ้นอยู่กับผู้พัฒนา) หนึ่งในตัวอย่างที่ชื่นชอบของ PHP split($pattern,$string)VS explode($delimiter,$string)- โชคดีในอดีตคือการคิดค่าเสื่อมราคา แต่จำนวนมากรหัสที่ใช้ในอดีตเมื่อพวกเขาต้องการเพียงอำนาจของในภายหลัง เห็นด้วย RegEx ให้เครื่องมือง่ายๆในการทำบางสิ่ง แต่ถ้าคุณไม่ต้องการพลังเต็มรูปแบบของการแสดงออกปกติพวกเขา
Rudu

4
เครื่องมือวิเคราะห์คำศัพท์อาจใช้ regexes พวกเขายังเป็นที่รู้จักกันในนาม tokenizers แต่พวกเขาไม่ใช่นักวิเคราะห์วากยสัมพันธ์ (หรือ parsers) ในการอ่านสตริงที่ซับซ้อนเพียงพอต้องใช้ tokenizer ในการอ่านสตริงเป็นโทเค็น (อาจเป็น regexes ซึ่งอาจไม่ขึ้นอยู่กับโทเค็นเซอร์) โทเค็นเหล่านี้ควรถูกส่งไปยัง parser ซึ่งจะประมวลผลกฎของไวยากรณ์ซึ่งไม่ได้ regexes
Axel

53

เกือบทุกคนที่ฉันรู้ว่าใครใช้นิพจน์ทั่วไปอย่างสม่ำเสมอ (ปุนตั้งใจ) มาจากพื้นหลังของ Unix-ish ที่พวกเขาใช้เครื่องมือที่ใช้ REs เหมือนการเขียนโปรแกรมระดับเฟิร์สคลาสเช่น grep, sed, awk และ Perl เนื่องจากแทบจะไม่มีค่าใช้จ่ายทางไวยากรณ์ในการใช้นิพจน์ทั่วไปผลผลิตของพวกเขาจึงเพิ่มขึ้นเมื่อพวกเขาทำ

ในทางตรงกันข้ามโปรแกรมเมอร์ที่ใช้ภาษาที่ REs เป็นไลบรารีภายนอกมักจะไม่พิจารณาว่านิพจน์ทั่วไปใดสามารถนำมาใช้กับตารางได้ โปรแกรมเมอร์ "เวลา - ค่าใช้จ่าย" สูงมากจนก) RE ไม่เคยเป็นส่วนหนึ่งของการฝึกอบรมหรือข) พวกเขาไม่ได้ "คิด" ในแง่ของ REs และชอบที่จะถอยกลับในรูปแบบที่คุ้นเคยมากกว่า


11
ใช่ฉันไม่เคยให้อภัย Python ในการสร้างไวยากรณ์ของ regex โดยใช้ห้องสมุด ฉันคิดว่ามันบริสุทธิ์กว่าสติ
slikts

7
ฉันมาจากพื้นหลัง unix ใช้ sed, awk & perl load และแน่นอนว่ามี grepping มากมาย แต่รู้ว่าเมื่อฉันใช้ regex มันเป็นแฮ็คแบบเขียนอย่างเดียวที่ฉันเกลียดการบำรุงรักษา เป็นเรื่องที่ดีสำหรับเชลล์สคริปต์ / ตัวจับเวลา แต่สำหรับการทำงานจริงสำหรับสิ่งที่ไม่เพียงแค่คว้าข้อมูลบางอย่างเพื่อบันทึกตอนนี้ฉันใช้ tokenizer / lexer / parser ที่เหมาะสมพร้อมกับไวยากรณ์ที่ชัดเจน สิ่งที่ฉันชอบทำทั้งหมด / ใด ๆ + อย่างหมดจดสามารถเพิ่มประสิทธิภาพด้วยตนเอง ฉันได้เรียนรู้วิธีที่ยากลำบากและหลายปีที่ผ่านมาการมีวินัยในตนเองในช่วงเริ่มต้นนั้นหมายถึงความพยายามน้อยลงในภายหลัง regex นั้นเป็นช่วงเวลาหนึ่งบนแป้นพิมพ์และอายุการใช้งานที่ขมวดคิ้ว
AndrewC

44

นิพจน์ทั่วไปช่วยให้คุณสามารถเขียนเครื่องจักร finite-state (FSM) ที่กำหนดเองได้ในวิธีกะทัดรัดเพื่อประมวลผลสตริงของอินพุต มีอย่างน้อยสองเหตุผลที่การใช้นิพจน์ทั่วไปนั้นยาก:

  • การพัฒนาซอฟต์แวร์ของโรงเรียนเก่านั้นเกี่ยวข้องกับการวางแผนรูปแบบกระดาษและความคิดที่รอบคอบ นิพจน์ทั่วไปเข้ากับโมเดลนี้ได้เป็นอย่างดีเนื่องจากการเขียนนิพจน์ที่มีประสิทธิภาพเกี่ยวข้องกับการจ้องมองมันอย่างมากทำให้เห็นเส้นทางของ FSM

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

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

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

หากมีการต่อต้านการใช้นิพจน์ปกติในหมู่นักพัฒนาซอฟต์แวร์วันนี้ฉันคิดว่าส่วนใหญ่เป็นเพราะปัจจัยทั้งสองนี้


4
มีเครื่องมือที่ดีเยี่ยมออกมีการ regexps การแก้ปัญหาคือ: regexbuddy.com
แจสเปอร์ BEKKERS

15
perl -Mre = debug -e "q [aabbcc] = ~ / ab * [cd] /"
Brad Gilbert

15
ฉันไม่คิดว่าฉันจะได้เห็นคำย่อ "FSM" โดยไม่ได้คิดถึง Flying Spaghetti Monster
Shabbyrobe

4
@Shabbyrobe: ฉันไม่ได้ตั้งใจจะรุกราน หากคุณต้องการคุณสามารถใช้ระบบ จำกัด ขอบเขตอัตโนมัติ (DFA)
Bill Karwin

37

คนมักจะคิดว่าการแสดงออกปกตินั้นยาก แต่นั่นเป็นเพราะพวกเขากำลังใช้พวกเขาผิด การเขียน one-liners ที่ซับซ้อนโดยไม่มีความคิดเห็นการเยื้องหรือการระบุชื่อ (คุณไม่อัดนิพจน์ SQL ที่ซับซ้อนของคุณในหนึ่งบรรทัดโดยไม่ต้องคอมเม้นท์เยื้องหรือนามแฝงใช่ไหม?) ใช่แล้วสำหรับคนจำนวนมากพวกเขาไม่สมเหตุสมผล

แต่ถ้างานของคุณมีอะไรจะทำอย่างไรกับการแยกข้อความ (ประมาณใด ๆ บนเว็บแอพลิเคชันออกมี ... ) และคุณไม่ทราบว่าการแสดงออกปกติคุณดูดที่งานของคุณและคุณจะเสียเวลาของคุณเองและของคุณ นายจ้าง. มีแหล่งข้อมูลที่ดีเยี่ยมเพื่อสอนคุณทุกอย่างเกี่ยวกับพวกเขาที่คุณจะต้องรู้และอีกมากมาย


2
ดี .. แตกต่างกันคือช่องว่างหลายมีความหมายใน regex ที่ในภาษาอื่น ๆ ที่พวกเขาทำไม่ได้และที่ว่าทำไมพวกเขามักจะหนึ่งสมุทร (ที่บางครั้งตัดไปหลายบรรทัด :)
Rado

14
@Rado: Perl ตัวอย่างเช่นมีโมดิฟายเออร์xสำหรับ regexes ที่ทำให้ whitespace ถูกละเว้น สิ่งนี้จะช่วยให้คุณใส่ regex ลงในสองสามบรรทัดและเพิ่มความคิดเห็น
Nathan Fellman

9
Python ก็เช่นกัน re.Xre.VERBOSEอาคา
Craig McQueen

2
ในทำนองเดียวกันโมดิxฟายเออร์ใน tcl ฉันเชื่อว่ามันค่อนข้างมาตรฐานตั้งแต่ tcl ซึ่งแตกต่างจากภาษาอื่น ๆ ไม่ได้ใช้ PCRE
slebetman

2
@AndrewC นั่นเป็นหนึ่งในการตีความที่ผิดขั้นต้นที่โพสต์นี้ได้รับ
Jasper Bekkers

28

เพราะพวกเขาขาดเครื่องมือการเรียนรู้ที่ได้รับความนิยมมากที่สุดใน IDEs ที่ยอมรับกันทั่วไป: ไม่มีตัวช่วยสร้าง Regex ไม่ได้เติมข้อความอัตโนมัติ คุณต้องเขียนโค้ดทั้งหมดด้วยตัวเอง


3
ถ้าอย่างนั้นคุณกำลังใช้ IDE ผิด ... แม้แต่ตัวแก้ไขข้อความของฉันก็ให้คำแนะนำ regex
CurtainDog

1
ในหมายเหตุด้าน Expresso และ Regex Coach เป็นเครื่องมือที่มีประโยชน์มากสำหรับการสร้างนิพจน์ทั่วไป
Mun

22
คุณจะเติมคำปกติในโลกอัตโนมัติอย่างไร?
AmbroseChapel

3
EditPad Pro มีการเน้นไวยากรณ์สำหรับ regexes ในช่องค้นหา แต่ฉันคิดว่ามันน่ารำคาญกว่ามีประโยชน์และปิดมันไว้ แต่ฉันก็ซาบซึ้งที่ทำให้ฉันรู้ว่าเมื่อฉันมีวงเล็บเหลี่ยมที่ไม่ตรงกัน; โดยเฉพาะวงเล็บอาจเป็นหมีที่คอยติดตาม
Alan Moore

2
@AmbroseChapel - ฉันสองสามปีที่ผ่านมาการอภิปรายนี้ แต่ฉันสร้างกลไกการเติมข้อความอัตโนมัติที่regexhero.net/tester มันริเริ่มโดยสร้างร่วมภายในรอบ()สี่เหลี่ยม[]หรือหยิก{}วงเล็บ นอกจากนี้ยังจะได้ผลจากแบ็กสแลช
Steve Wortham

17

" นิพจน์ทั่วไป: ตอนนี้คุณมีปัญหาสองข้อ " เป็นบทความที่ยอดเยี่ยมจาก Jeff Atwood ในเรื่องนี้ โดยทั่วไปการแสดงผลปกติจะ "ยาก"! พวกเขาสามารถสร้างปัญหาใหม่ อย่างไรก็ตามมันมีประสิทธิภาพ


16

ฉันไม่คิดว่าพวกเขาโต้เถียงกัน

ฉันคิดว่าคุณตอบคำถามของคุณเองเพราะคุณชี้ให้เห็นว่ามันโง่แค่ไหนที่จะใช้มันทุกที่ ( ไม่ใช่ทุกอย่างเป็นภาษาปกติ 2 ) หรือเพื่อหลีกเลี่ยงการใช้มันเลย คุณโปรแกรมเมอร์ต้องทำการตัดสินใจอย่างชาญฉลาดว่านิพจน์ทั่วไปจะช่วยให้รหัสหรือทำร้ายมันเมื่อใด เมื่อต้องเผชิญกับการตัดสินใจเช่นนี้สิ่งสำคัญสองประการที่ควรคำนึงถึงคือการบำรุงรักษา (ซึ่งหมายถึงการอ่านได้ง่าย) และการเพิ่มความสามารถ

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

http://docs.python.org/howto/regex

แม้ว่าหน้านั้นจะพูดเกี่ยวกับนิพจน์ทั่วไปในบริบทของ Python แต่ฉันพบว่าข้อมูลนั้นมีประโยชน์มากในที่อื่น มีบางสิ่งที่เฉพาะเจาะจงของงูหลาม แต่ฉันเชื่อว่ามันถูกบันทึกไว้อย่างชัดเจนและจดจำได้ง่าย


2
ดูเหมือนว่าหน้าเว็บจะย้ายไปที่docs.python.org/howto/regex
Dominic K

@ DMan ขอบคุณ ฉันจะแก้ไขคำตอบเพื่อสะท้อน
allyourcode

11

นิพจน์ทั่วไปเป็นการ จำกัด ตัวดำเนินการทางคณิตศาสตร์ที่มีต่อตัวเลขและฉันจะไม่พิจารณาว่ามันขัดแย้งกันหรือไม่ ฉันคิดว่าแม้กระทั่งนักกิจกรรมOO ที่มีความเป็นธรรมอย่างตัวฉันเอง


7

ปัญหาคือว่า regexes อาจมีประสิทธิภาพเพื่อให้คุณสามารถทำสิ่งต่าง ๆ กับพวกเขาที่คุณควรใช้สิ่งที่แตกต่างกัน

โปรแกรมเมอร์ที่ดีควรรู้ว่าจะใช้ที่ไหนและที่ไหนดี ตัวอย่างทั่วไปคือการแยกวิเคราะห์ภาษาที่ไม่ปกติ (ดูที่การตัดสินใจว่าภาษานั้นปกติหรือไม่ )

ฉันคิดว่าคุณจะผิดพลาดไม่ได้ถ้าในตอนแรกคุณ จำกัด ตัวเองไว้ที่การแสดงออกปกติจริง ๆ (ไม่มีส่วนขยาย) ส่วนขยายบางอย่างสามารถทำให้ชีวิตของคุณง่ายขึ้นเล็กน้อย แต่ถ้าคุณพบสิ่งที่ยากที่จะแสดงว่าเป็นregex จริงนี่อาจเป็นเครื่องบ่งชี้ว่า regex ไม่ใช่เครื่องมือที่เหมาะสม


5

คุณเกือบจะถูกถามว่าทำไมการโต้กลับของถึงโต้เถียงกัน

โดยทั่วไปเมื่อคุณได้รับพลัง "ชัดเจน" ผู้คนมีแนวโน้มที่จะทำร้ายพวกเขาในสถานการณ์ที่พวกเขาไม่ได้เป็นตัวเลือกที่ดีที่สุด จำนวนคนที่ขอให้แยกวิเคราะห์ CSV หรือ XML หรือ HTML ใน regexes ทำให้ฉันประหลาดใจ มันเป็นเครื่องมือที่ผิดสำหรับงาน แต่ผู้ใช้บางคนยืนยันในการใช้ regexes อยู่ดี

โดยส่วนตัวแล้วฉันพยายามค้นหาสื่อที่มีความสุข - ใช้ regexes สำหรับสิ่งที่พวกเขาดีและหลีกเลี่ยงพวกเขาเมื่อพวกเขาน้อยกว่าที่เหมาะสม

โปรดทราบว่า regex ยังสามารถใช้ในการแยกวิเคราะห์ CSV, XML, HTML และอื่น ๆ แต่มักจะไม่ได้อยู่ใน regex เดียว


แน่ใจว่าคุณสามารถวิเคราะห์รูปแบบใด ๆ เหล่านี้ใน regex เดียวนั่นคือพลังของ regexes ที่รัก! ไม่ว่าคุณจะต้องการทำสิ่งนั้นหรือไม่
แจสเปอร์

4

ฉันไม่คิดว่า "แย้ง" เป็นคำที่ถูกต้อง

แต่ฉันได้เห็นตัวอย่างมากมายที่ผู้คนพูดว่า "อะไรคือนิพจน์ปกติที่ฉันต้องทำเช่นนี้และเช่นการจัดการสตริง?" ซึ่งเป็นปัญหา XY

กล่าวอีกนัยหนึ่งพวกเขาได้เริ่มต้นจากการสันนิษฐานว่า regex เป็นสิ่งที่พวกเขาต้องการ แต่พวกเขาควรจะดีกว่าด้วย split () การแปลเช่น perl's tr /// ที่ตัวละครถูกแทนที่ด้วยตัวอื่นหรือ เพียงดัชนี ()


4

วิชานี้เป็นวิชาที่น่าสนใจ ผู้สนใจรักการเต้น regexp
หลายคนดูเหมือนจะสับสนกับความกระชับของสูตรด้วยประสิทธิภาพ ยิ่งไปกว่านั้น regexp ที่ต้องใช้ความคิดจำนวนมากสร้างความพึงพอใจอย่างมากให้กับผู้เขียนซึ่งทำให้ถูกต้องตามกฎหมายทันที

แต่ ... regexps สะดวกสบายมากเมื่อประสิทธิภาพไม่ใช่ปัญหาและคุณต้องจัดการกับข้อความใน Perl อย่างรวดเร็ว อีกทั้งในขณะที่ประสิทธิภาพก็คือปัญหาหนึ่งอาจไม่พยายามเอาชนะไลบรารี regexp โดยใช้อัลกอริทึมแบบโฮมเมดที่อาจ buggy หรือมีประสิทธิภาพน้อยลง

นอกจากนี้ยังมีหลายเหตุผลที่ regexps ถูกวิจารณ์อย่างไม่เป็นธรรมเช่น

  • regexp นั้นไม่มีประสิทธิภาพเพราะการสร้างอันดับหนึ่งไม่ชัดเจน
  • โปรแกรมเมอร์บางคน "ลืม" เพื่อรวบรวมเพียงครั้งเดียว regexp ที่จะใช้หลายครั้ง (เช่นรูปแบบคงที่ใน Java)
  • โปรแกรมเมอร์บางคนใช้กลยุทธ์การลองผิดลองถูก - ทำงานได้น้อยลงกับ regexps!

4

สิ่งที่ฉันคิดว่าคือการเรียนรู้ Regex และการบำรุงรักษา regex ทำให้ไม่เป็นที่นิยมนักพัฒนาส่วนใหญ่จะขี้เกียจหรือส่วนใหญ่พึ่งพาห้องสมุดภายนอกเพื่อทำสิ่งที่แยกสำหรับพวกเขา ... พวกเขาพึ่งพา google สำหรับคำตอบและถามในฟอรัม รหัสที่สมบูรณ์สำหรับปัญหาของพวกเขา แต่เมื่อมาใช้งานหรือแก้ไข / บำรุงรักษา regex พวกเขาก็ล้มเหลว

มีคำพูดยอดนิยมว่า "เพื่อน ๆ อย่าปล่อยให้เพื่อนใช้ Regex สำหรับการแยกวิเคราะห์ HTML"

แต่เท่าที่ฉันกังวลฉันได้ทำ parsers HTML ที่สมบูรณ์โดยใช้ Regex และฉันพบว่าตัวเอง regex ดีกว่าในการแยกสตริง html ทั้ง speed-wise และ memory-wise (ถ้าคุณมีความคิดว่าคุณจะทำอย่างไร :)


2
ฉันคิดว่ามันไม่สุภาพที่จะเขียนนักพัฒนาส่วนใหญ่ ... ขี้เกียจ ฉันจะบอกว่าซินแทกซ์นั้นซับซ้อนมากไม่สามารถหยั่งรู้ได้และเต็มไปด้วย gotchas ถึงผู้ที่ยังไม่ได้เริ่มต้นซึ่งนำไปสู่อุปสรรคที่สูงในการเข้า ด้วยเหตุผลเดียวกัน Perl มีชื่อเสียง "ไม่ดี" สำหรับหลาย ๆ คน แต่ยังเป็นภาษาที่ทรงพลังมาก มันเหมือนกับการพยายามอ่านนิพจน์ทางคณิตศาสตร์ก่อนที่คุณจะรู้สัญลักษณ์ เป็นเรื่องที่น่ากังวลและนักพัฒนาจะต้องพิจารณาคดีด้วยเวลาที่จะรู้ว่าพวกเขาจะได้รับประโยชน์จากการเรียนรู้ไวยากรณ์นั้น
Katastic Voyage

คุณจะพลาดกรณีขอบใน HTML เพราะ HTML ไม่ใช่ภาษาปกติ คุณปลอดภัยหากคุณตั้งใจจะแยกชุดย่อยที่เป็นที่รู้จักของ HTML
Boyang

2

การแสดงออกปกติเป็นความลึกลับที่ร้ายแรงสำหรับผู้คนมากมายรวมถึงตัวฉันด้วย มันใช้งานได้ดี แต่มันก็เหมือนกับการดูสมการทางคณิตศาสตร์ ฉันยินดีที่จะรายงานว่ามีใครบางคนที่ได้สร้างในที่สุดก็เป็นสถานที่รวมของฟังก์ชั่นการแสดงออกปกติต่างๆที่http://regexlib.com/ ตอนนี้ถ้า Microsoft จะสร้างคลาสนิพจน์ปกติที่จะทำสิ่งทั่วไปโดยอัตโนมัติเช่นการกำจัดจดหมายหรือการกรองวันที่


2
คุณไม่มีจุด แนวคิดของ regexes คือคุณใช้เวลาในการเรียนรู้และเมื่อคุณทำเสร็จแล้วคุณไม่จำเป็นต้องมีคลาส "อ่านวันที่" ที่มีมนต์ขลังอีกต่อไป แต่ใช้ความพยายามน้อยมากสำหรับพวกเขา ยิ่งไปกว่านั้นมันจะใช้ความพยายามเพียงเล็กน้อยในการเขียนสำหรับ "yyyy / mm / dd" ตามที่ใช้ในการเขียนหนึ่งสำหรับ "mm-dd-yyyy" หรือแม้แต่หนึ่งสำหรับ "mm-yyyy / dd" (ซึ่งชนะ เกิดขึ้นบ่อยครั้ง แต่เป็นตัวอย่างของวิธีที่คุณสามารถทำสิ่งที่คลาสเวทไม่สามารถทำได้ ")
นิล

1

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

หากคุณต้องการวางตะปูบนกำแพงอย่าใช้ค้อน ใช่มันใช้งานได้ แต่พอถึงเวลาที่คุณได้ค้อนฉันสามารถใส่ 20 tacks ในกำแพงได้

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


0

ในขณะที่ฉันคิดว่า regexes เป็นเครื่องมือสำคัญสิ่งที่น่ารำคาญที่สุดเกี่ยวกับพวกเขาคือมีการใช้งานที่แตกต่างกัน ความแตกต่างเล็กน้อยในไวยากรณ์ตัวดัดแปลงและ - โดยเฉพาะ - "ความโลภ" สามารถทำให้สิ่งต่าง ๆ วุ่นวายจริง ๆ ต้องใช้การทดลองและข้อผิดพลาดและบางครั้งก็สร้างข้อผิดพลาดที่ทำให้งง


การใช้งาน regex แตกต่างกันอย่างไรในแนวทางของพวกเขาในการจับคู่สูงสุดสิ่งที่ฉันคิดว่าคุณกำลังเรียกว่า "ความโลภ"? คุณหมายถึงความแตกต่างระหว่างซีแมนทิกส์ซ้ายสุดยาวที่สุดและยาวซ้ายสุดหรือไม่? นั่นคือความแตกต่างเดียวที่ฉันรู้ คือไม่ว่าจะเป็นความโลภความอยากปั้นหรือในทางกลับกัน
tchrist

0

ในบางกรณีฉันคิดว่าคุณต้องใช้มัน ตัวอย่างเช่นการสร้างเล็กซ์เซอร์

ในความคิดของฉันนี่เป็นมุมมองของคนที่สามารถเขียน regexp และคนที่ไม่ (หรือแทบจะไม่) ฉันเป็นคนที่คิดว่านี่เป็นตัวอย่างที่ดีในการตรวจสอบความถูกต้องของแบบฟอร์มไม่ว่าจะเป็นจาวาสคริปต์เพื่อเตือนผู้ใช้หรือภาษาฝั่งเซิร์ฟเวอร์


0

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


1
การอ่านนิพจน์ทั่วไปนั้นเป็นเรื่องยากเฉพาะเมื่อโปรแกรมเมอร์ที่สร้างขึ้นมาไม่สามารถใช้ช่องว่างความคิดเห็นตัวระบุตัวเลขและตัวอักษรและอาจฝังรูทีนย่อยผ่านการดำเนินการล่าช้า กล่าวโดยสรุปเทคนิควิศวกรรมซอฟต์แวร์ทั้งหมดที่ใช้กับการเขียนโปรแกรมทั่วไปควรปฏิบัติตามด้วยการแสดงออกปกติ หากหลักการเหล่านี้ถูกละเว้นนักเขียนจะไม่สร้างรหัสมืออาชีพ
tchrist

ฉันคิดว่าผู้จัดการของคุณไม่ทราบว่า "ฮีโร่ที่แท้จริงของการเขียนโปรแกรมคือผู้ที่เขียนโค้ดเชิงลบ"
Rajeev

หากผู้จัดการของคุณกำลังจะทำให้คุณประสบความสำเร็จในการทำงานด้วยรหัส 3 บรรทัด (รวมถึง regexps) ในขณะที่ชื่นชมเพื่อนร่วมงานของ doofus บางคนที่ทำงานใน Assembler 900 สาย ... ฉันขอแนะนำให้หางานใหม่
Phil Perry

0

ระบบนิพจน์ทั่วไปที่มีคุณค่าเช่นที่ใช้ใน lex และ yacc สำหรับนิยามคอมไพเลอร์นั้นดีมีประโยชน์มากและสะอาด ในระบบเหล่านี้ประเภทการแสดงออกถูกกำหนดในแง่ของคนอื่น มันเป็นเสียงยักษ์สายหนึ่งที่ไม่สามารถอ่านได้ซึ่งมีรูปแบบปกติที่พบในรหัส perl และ sed (ฯลฯ ) ที่มีรูปแบบ 'แย้ง' (ขยะ)


-4

การใช้ที่ถูกต้องและปกติที่สุดสำหรับ regex สำหรับการตรวจสอบรูปแบบที่อยู่อีเมล

นั่นเป็นแอพพลิเคชั่นที่ดีของมัน

ฉันใช้นิพจน์ทั่วไปนับครั้งไม่ถ้วนเป็นเพียงครั้งเดียวใน TextPad เพื่อนวดไฟล์แบนสร้างไฟล์ csv สร้างคำสั่งแทรก SQL และเรียงลำดับของสิ่งนั้น

นิพจน์ทั่วไปที่เขียนดีไม่ควรช้าเกินไป โดยทั่วไปแล้วตัวเลือกอื่น ๆ เช่นการโทรเพื่อแทนที่เป็นตัวเลือกที่ช้ากว่ามาก อาจทำได้ในครั้งเดียว

สถานการณ์จำนวนมากเรียกร้องให้มีการแสดงออกปกติและไม่มีอะไรอื่น

การแทนที่อักขระที่ไม่ใช่การพิมพ์พิเศษด้วยอักขระที่ไม่มีพิษภัยเป็นการใช้งานที่ดีอีกอย่างหนึ่ง

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


10
ประสบการณ์แสดงให้เห็นว่าจริง ๆ แล้ว regexes เป็นเครื่องมือที่ไม่ดีนักในการตรวจสอบรูปแบบที่อยู่อีเมล ตัวตรวจสอบรูปแบบที่สมบูรณ์อย่างแท้จริงที่นำมาใช้เป็น regex เป็นความน่าพิศวงหลายร้อยตัวในขณะที่ตัวตรวจสอบความถูกต้อง "ดีพอ" ส่วนใหญ่ที่สั้นกว่าที่คนส่วนใหญ่ใช้เวลา 5 นาทีในการสร้างจะปฏิเสธที่อยู่ที่ถูกต้อง
เดฟ Sherohman

ฉันได้ยินคุณเพื่อน ฉันกำลังพูดถึง "ดีพอ" และในขณะที่แนวเสียงขนาดใหญ่อาจมีขนาดใหญ่ในทางทฤษฎีให้พิจารณาเปอร์เซ็นต์ของความครอบคลุมที่คุณได้รับในการแสดงออกสั้น ๆ ฉันก็เคยเห็นความน่าประหลาดใจ แต่อะไรคือทางเลือกที่สวยงามของคุณ?
คริสมอร์ลี่ย์

2
ฉันใช้บางอย่างเช่น \ w @ \ w +. \ w + เพื่อค้นหาที่อยู่อีเมลอย่างรวดเร็วในไดเรกทอรีขนาดใหญ่ของไฟล์ที่ความเร็วมีความสำคัญและผลบวกปลอมหรือเชิงลบที่ไม่สำคัญไม่สำคัญ แต่วิธีที่ดีที่สุดในการตรวจสอบความถูกต้องของที่อยู่อีเมลคือการส่งอีเมลไปให้
RossFabricant

ใช่อีเมลข้อมูลจำเพาะที่อยู่เป็นระเบียบที่น่ารังเกียจstackoverflow.com/questions/611775/ …
Nick Van Brunt

@Nick, @Dave: การตรวจสอบที่อยู่อีเมลไม่จำเป็นต้องยุ่งเหยิง
tchrist
โดยการใช้ไซต์ของเรา หมายความว่าคุณได้อ่านและทำความเข้าใจนโยบายคุกกี้และนโยบายความเป็นส่วนตัวของเราแล้ว
Licensed under cc by-sa 3.0 with attribution required.