2009-07-28 12 views
6

मैं कुछ पर्ल कर रहा हूं और अपना घोंसला देख रहा हूं "अगर" कथन मुझे पागल कर रहा है। मैंने उनमें से कुछ को दूसरे खंड में गार्ड ब्लॉक के साथ कम करने में कामयाब रहे, लेकिन मैं यहां फंस गया हूं।क्या मुझे पर्ले में बयान देते हुए घोंसला से बचना चाहिए?

क्या आपको लगता है कि मैं कोड छोड़ सकता हूं, या क्या निम्नलिखित को दोबारा करने का एक "उचित" तरीका है? (मैं पर्ल के लिए अपेक्षाकृत नया मानता हूं)

यह वास्तव में एक सबराउटिन है जो सूची (बाहरी फ़ाइल) के प्रत्येक पैरामीटर पर उपयोगकर्ता इनपुट मांगता है। $ [3] मिलान पैटर्न है, $ [2] माना गया पैरामीटर (NULL यदि कोई नहीं है) के लिए डिफ़ॉल्ट मान है, $ _ [1] निर्दिष्ट करता है कि यह अनिवार्य है या नहीं। 'अगला' कथन अगले पैरामीटर को पढ़ता है (जबकि लूप)।

हर किसी की मदद से (धन्यवाद!), यहां नवीनतम संस्करण है।

100   if ($input ne '' && ($input !~ $match || $input =~ /'.+'/)) { 
101    print "! Format not respected. Match : /$match/ (without \' \')\n"; 
102    next; 
103   } 
104   if ($input eq '') { 
105    if ($default eq 'NULL') { 
106     if ($manda eq 'y') { 
107      print "! Mandatory parameter not filled in\n"; 
108      next; 
109     } 
110     print "+ Ignoring parameter.\n"; 
111     $input = ''; 
112    } 
113    else { 
114     print "+ Using default value\n"; 
115     $input = $default; 
116    } 
117   } 

98  if($input eq ''){ 
99    if($_[2] eq 'NULL'){ 
100     if($_[1] eq 'y'){ 
101      print "! Mandatory parameter not filled in\n"; 
102      next; 
103     } 
104     else{ 
105      print "+ Ignoring parameter.\n"; 
106      $input = ''; 
107     } 
108    } 
109    else{ 
110     print "+ Using default value\n"; 
111     $input = $_[2]; 
112    } 
113   } 
114   elsif($input !~ $_[3] || $input =~ /'.+'/){ 
115     print "! Format not respected. Match : /$_[3]/ (without \' \')\n"; 
116     next; 
117    } 
118   } 
+1

विशेष रूप से यह है कि आपको उन घोंसले के बारे में पागल कर रहा है? – innaM

+0

मुझे नहीं पता, मुझे लगता है कि लिखने का एक और तरीका है ... –

उत्तर

10

यहाँ अराजकता के एक से थोड़ा अधिक पठनीय संस्करण है 'जवाब:

# Set sane variable names... 
my ($is_required, $default, $pattern) = @_ 

# Convert the external string convention for simpler evaluation... 
$default = undef if $default eq 'NULL' 

# Refuse problematic input before going any further... 
if ($input ne '' && $input !~ $pattern || $input =~ /'.+'/) { 
    print "! Format not respected. Match : /$pattern/ (without \' \')\n"; 
    next; 
} 


# If there was no input string... 
if($input eq '') { 

    # Set the default, if one was provided... 
    if($default) { 
     print "+ Using default value\n"; 
     $input = $default; 
    } 
    # otherwise, complain if a default was required... 
    else { 
     if($is_required eq 'y'){ 
      print "! Mandatory parameter not filled in\n"; 
      next; 
     } 
     print "+ Ignoring parameter (no input or default provided).\n"; 
    } 
} 

महत्वपूर्ण बिंदु हैं:

  • आपसे किसी और की जरूरत नहीं है अगर आप के साथ वर्तमान पाश बाहर निकलने रहे हैं अगले
  • असाधारण मामलों को पहले
  • पर संभाला जाना चाहिए नामित चर का उपयोग करके पठनीयता में काफी सुधार
+0

इसके लिए धन्यवाद। हमारे उत्तरों पार हो गए (मेरी पहली पोस्ट संपादित देखें)। बीटीडब्ल्यू, मेरे कोड में, $__ququired उपयोगकर्ता को भरने के लिए मजबूर करता है, यह कोई शिकायत नहीं है: पी (हालांकि कुछ भी नहीं बदलता है और आपने पूरे सबराउटिन को नहीं पढ़ा है) –

+0

डबल पोस्ट करने के लिए खेद है, लेकिन मुझे टिप्पणी करने का आपका तरीका पसंद है ; और "आपने पढ़ा नहीं है" मेरा मतलब था "मैंने पोस्ट नहीं किया है"। –

+0

धन्यवाद, हालांकि मैं किसी भी क्रेडिट का दावा नहीं कर सकता। टिप्पणी शैली डेमियन Conway है - मैंने इसे अपनी सामग्री पढ़ने के बाद अपनाया क्योंकि मुझे यह भी पसंद आया। ;) –

1

अगर बयान तो मुझे लगता है कि उन लोगों के साथ कुछ भी गलत नहीं है, तो आप तर्क नेस्ट की आवश्यकता है।

हालांकि, अगर आप सिर्फ एक छोटे से अधिक सफेद स्थान और

  • का उपयोग करना द्वारा

    1. अपने कोड की पठनीयता में सुधार कर सकता है के बजाय अपने खुद के वैरिएबल का उपयोग कर @_

    Isn 'पर सीधे ऑपरेटिंग तक यह थोड़ा और पठनीय नहीं है?

    98  if ($input eq '') { 
    99    if ($default eq 'NULL'){ 
    100     if ($input eq 'y'){ 
    101      print "! Mandatory parameter not filled in\n"; 
    102      next; 
    103     } 
    104     else { 
    105      print "+ Ignoring parameter.\n"; 
    106      $input = ''; 
    107     } 
    108    } 
    109    else { 
    110     print "+ Using default value\n"; 
    111     $input = $default; 
    112    } 
    113   } 
    114   elsif ($input !~ $foo || $input =~ /'.+'/) { 
    115     print "! Format not respected. Match : /$foo/ (without \' \')\n"; 
    116     next; 
    117    } 
    118   } 
    
  • +0

    बिंदु के बारे में 1., मैं थोड़ी देर में पर्ल्टिडी का उपयोग कर रहा हूं। मैं वर्तमान में समस्याओं को हल करने और पहले से डीबग करने की कोशिश कर रहा हूं। 2. मैंने पढ़ा (ओरेली की किताब और अन्य जगहों में) कि $ _ और $ @ का व्यापक रूप से उपयोग किया गया था, बिना किसी कमी के उल्लेख किए? –

    +0

    1. समस्याओं को हल करने की कोशिश करना कोड पढ़ने में आसान है। 2. दोष पठनीयता है। $ _ [X] के आपके विभिन्न उपयोगों को प्रतिस्थापित करते समय, उदाहरण के लिए, मैंने तुरंत देखा कि उन चरों को पकड़ने का आपका विवरण पूरी तरह से सही नहीं हो सकता है। – innaM

    +0

    1. आप बिल्कुल सही हैं। मुझे कोड पसंद है, लेकिन यह निश्चित रूप से दूसरों द्वारा बनाए रखा जाएगा (पहले आप)। 2. @_ एक सरणी है जो फ़ंक्शन में पास (मान द्वारा) पैरामीटर की सूची रखती है। सही ? $ _ के लिए, मैं केवल इसका उपयोग कर रहा हूं जब r/w (in) एक फ़ाइल हैंडल। –

    2

    सामान्य अभ्यास आपके सरणी इंडेक्स के लिए स्थिरांक को परिभाषित करना है, और उन्हें सार्थक नाम देना है। जैसे:

    use constant MANDATORY => 1, 
          DEFAULT => 2, 
          PATTERN => 3; 
    ... 
    if($_[DEFAULT] eq 'NULL') { 
        ... 
    } 
    
    घोंसले के रूप में

    जहां तक ​​- आप अक्सर (नेस्टिंग कम के स्तर पर रखने के अर्थ) मांगपत्र को कम करने की कोशिश करनी चाहिए, लेकिन कोड समझा जा सकता रखने की कीमत पर ऐसा कभी नहीं। मुझे घोंसले के स्तर के साथ कोई समस्या नहीं है, लेकिन यह आपके कोड का एक छोटा सा कट भी है। यदि यह वास्तव में एक मुद्दा है, तो आप अलग-अलग subroutines में शर्तों को तोड़ सकते हैं।

    +0

    जैसा कि मैंने कहा, यह एक सबराउटिन है, मेरे सभी चर स्थानीय हैं। इसलिए मैं "उपयोग" कथन का उपयोग नहीं कर सकता? निस्संदेह कोड के बाकी हिस्सों पर कोई समस्या नहीं है, शुक्र है। आपके उत्तर के लिए धन्यवाद। –

    +1

    'निरंतर उपयोग' में कुछ कमीएं हैं। निरंतर उपयोग के साथ बनाए गए स्थिरांक को अलग-अलग नहीं किया जा सकता है (उदाहरण के लिए तारों में), क्योंकि उनके पास कोई सिगिल नहीं है, और रनटाइम पर स्पष्ट रूप से स्कॉप्ड नहीं किया जाता है। वे पैकेज-स्कोप्ड हैं और संकलन समय पर उत्पन्न होते हैं। यदि आपके पास रनटाइम पर निरंतर सेट है, तो यह एक समस्या है, उदा। एक समारोह से। यह डैमियन कॉनवे द्वारा 'पर्ल बेस्ट प्रैक्टिस' पुस्तक में उत्कृष्ट उदाहरणों के साथ और उत्कृष्ट उदाहरणों के साथ वर्णित है। –

    0

    यह देखते हुए कि आप शायद नहीं तो बिल्कुल नहीं।

    क्या बेहतर हो सकता है एक switch case है एक स्पेगेटी goto करेंगे,।

    +0

    मैंने अपना सबक सीखा: गेटो हेल है। ;) इसके बारे में कभी भी सोचा नहीं। स्विच केस वास्तव में यहां लागू नहीं होता है, क्योंकि मैं 4 अलग-अलग चर का परीक्षण कर रहा हूं। –

    +0

    क्या आपका मतलब 'दिया '/' कब' नहीं है? –

    +0

    क्या यह केवल 'उपयोग सुविधा' या 'उपयोग स्विच' perl 6.0 '' के साथ लागू नहीं किया गया है? –

    3
    if($input ne '' && ($input !~ $_[3] || $input =~ /'.+'/)) { 
        print "! Format not respected. Match : /$_[3]/ (without \' \')\n"; 
        next; 
    } 
    if($input eq '') { 
        if($_[2] eq 'NULL') { 
         if($_[1] eq 'y'){ 
          print "! Mandatory parameter not filled in\n"; 
          next; 
         } 
         print "+ Ignoring parameter.\n"; 
         $input = ''; 
        } else { 
         print "+ Using default value\n"; 
         $input = $_[2]; 
        } 
    } 
    
    +0

    मुझे यह पसंद है! धन्यवाद ! (cuddled अन्य को छोड़कर: पी) –

    0

    यदि आप अन्य सभी को पसंद नहीं करते हैं तो आप निम्न को सरल बना सकते हैं।

    if($input eq ''){ 
        $input = $_[2]; 
        $output = "+ Using default value\n"; 
        if($_[2] eq 'NULL'){ 
         $input = ''; 
         $output = "+ Ignoring parameter.\n"; 
         if($_[1] eq 'y'){ 
          $output = "! Mandatory parameter not filled in\n"; 
         } 
        } 
    } 
    elsif($input !~ $_[3] || $input =~ /'.+'/){ 
        $output = "! Format not respected. Match : /$_[3]/ (without \' \')\n"; 
    } 
    print $output; 
    
    +0

    imho, यह कुछ पठनीयता खो दिया। वैसे भी धन्यवाद;) –

    3

    मुख्य चिंता कोड को पठनीय रखने के लिए है।

    यदि आप कथन के साथ नेस्टेड के साथ पठनीय कोड प्राप्त कर सकते हैं, तो आगे बढ़ें। लेकिन हर समय सामान्य ज्ञान सक्रिय रखें।

    +0

    क्या आपको अपना कोड बनाए रखना होगा, क्या आपको ऐसा करने में कठिनाई होगी? –

    +0

    @ इसाक, नहीं। (लेकिन मुझे कोड पढ़ने के लिए कड़ी मेहनत रखने के लिए प्रशिक्षित किया गया है इसलिए मैं एक अच्छा संदर्भ नहीं हूं)। –

    -2

    मुझे लगता है आप इसे बाहर समतल तर्क संयोजन कर सकता है:

    if(($input eq '')&&($_[2] eq 'NULL')&&($_[1] eq 'y')){ 
        print "! Mandatory parameter not filled in\n"; 
        next; 
    } 
    
    elsif(($input eq '')&&($_[2] eq 'NULL')){ 
        print "+ Ignoring parameter.\n"; 
        $input = ''; 
    } 
    
    elsif($input eq ''){ 
        print "+ Using default value\n"; 
        $input = $_[2]; 
        next; 
    } 
    
    
    elsif($input !~ $_[3] || $input =~ /'.+'/){ 
        print "! Format not respected. Match : /$_[3]/ (without \' \')\n"; 
    } 
    
    print $output; 
    

    तो फिर तुम एक स्विच इस्तेमाल कर सकते हैं यह थोड़ा बेहतर बनाने के लिए।

    +0

    यह वास्तव में मेरा पिछला संस्करण था, '&&' परीक्षणों ने मुझे अनुकूल नहीं किया, हालांकि। –

    +0

    यह पठनीयता और गति दोनों को कम करता है। – Imagist

    +0

    यह पर्ल भी नहीं है। पर्ल में 'elseif' केवल' elsif' नहीं है। –

    0

    मुझे लगता है कि घोंसले के संबंध में चिंताओं के लिए मुख्य (यदि न केवल) कारण एल्गोरिदम जटिलता है। अन्य मामलों में आपको पठनीयता और रखरखाव के बारे में चिंता करनी चाहिए, जिसे प्रोपोयर टिप्पणी और इंडेंटेशन के साथ संबोधित किया जा सकता है।

    मैं हमेशा मेरा पुराने कोड, न केवल पठनीयता पर प्रतिक्रिया करने के लिए, लेकिन यह भी तकनीक पर पढ़ने के लिए maintanability में एक अच्छा व्यायाम लगता है ...

    4

    एक वैकल्पिक दृष्टिकोण है कि कभी कभी पठनीयता के साथ मदद करता है कुछ या सभी डाल करने के लिए है अच्छी तरह से नाम कोड संदर्भ में शाखाओं के। यहां विचार पर एक शुरुआत है:

    $format_not_respected = sub { 
        return 0 if ...; 
        print "! Format not respected...."; 
        return 1; 
    } 
    $missing_mandatory_param = sub { 
        return 0 if ...; 
        print "! Mandatory parameter not filled in\n"; 
        return 1; 
    } 
    
    next if $format_not_respected->(); 
    next if $missing_mandatory_param->(); 
    etc... 
    
    +0

    मुझे इसके बारे में पता नहीं था, धन्यवाद! भले ही मेरे मामले में, मैं पहले से ही एक सबराउटिन (नेस्टेड अगर उप-सब-रूटीन, यह सवाल है) में है, जो कि अन्य स्क्रिप्ट के लिए आसान हो सकता है। –

    +0

    यह हर बार जब आप इस फ़ंक्शन को कॉल करते हैं तो कुछ सबस को संकलित करने जा रहा है - क्या वह * वास्तव में * आप क्या करना चाहते हैं? यह एक साफ विचार है - और मैंने आपको एक अप दिया है, लेकिन अगर इसे बहुत कुछ कहा जा रहा है, तो बेहतर है कि कैप्चर व्यवहार का उपयोग न करें। (मुझे लगता है।) – Axeman

    संबंधित मुद्दे