2009-08-11 19 views
30

सीखना रूबी का उपयोग करें। मैं धारणा के तहत कर रहा हूँ के रूप में इस बूलियन गुण नाम दिया जाना चाहिए कि:रूबी: बूलियन विशेषता नामकरण सम्मेलन और

my_boolean_attribute? 

हालांकि, जब निम्न कार्य करने का प्रयास कर रहा सिंटैक्स त्रुटि मिलती है: "?"

class MyClass 
    attr_accessor :my_boolean_attribute? 

    def initialize 
    :my_boolean_attribute? = false 
    end 
end 

जाहिर माणिक नफरत है । क्या यह सम्मेलन है? मैं क्या गलत कर रहा हूं?

उत्तर

40

संपादित करें: तीन साल बाद; बार, वे एक-'बदल रहे हैं ...

Julik's answer सरल और सबसे अच्छा तरीका है समस्या से निपटने के लिए इन दिनों है:

class Foo 
    attr_accessor :dead 
    alias_method :dead?, :dead # will pick up the reader method 
end 

मूल प्रश्न के लिए मेरा जवाब भावी पीढ़ी के लिए, इस प्रकार है ...


लघु संस्करण:

आप एक उदाहरण चर के नाम पर एक प्रश्न चिह्न का उपयोग नहीं कर सकते हैं।

अब संस्करण: -:

def foo 
    @foo 
end 

def foo=(newfoo) 
    @foo = newfoo 
end 

इसके अलावा, प्रश्न चिह्न प्रत्यय ज्यादातर बस है

उदाहरण के लिए, attr_accessor :foo यह बस धारणात्मक निम्नलिखित के लिए वाक्यात्मक चीनी का एक सा यह इंगित करने के लिए एक सम्मेलन है कि एक विधि का वापसी मूल्य एक बूलियन है।

सबसे अच्छा सन्निकटन मैं तुम यहाँ के लिए क्या जा रहे हैं के लिए कर सकते हैं ...

class MyClass 

    def initialize 
    @awesome = true 
    end 

    def awesome? 
    @awesome 
    end 

end 

इस मामले में, हो सकता है एक मामले attr_accessor प्रयोग करने के लिए किए जाने के लिए - सब के बाद, यह स्पष्ट हो सकता है आप सीधे एक बुलियन विशेषता के साथ काम कर रहे हैं। आम तौर पर, जब मैं एक विधि को कार्यान्वित कर रहा हूं, तो मैं प्रश्न-चिह्न प्रत्यय को सहेजता हूं जिसका बूलियन रिटर्न मान केवल एक विशेषता के मूल्य की तुलना में थोड़ा अधिक जटिल स्थितियों पर आधारित होता है।

चीयर्स!


संपादित करें, दो साल बाद, हाल ही में टिप्पणी के बाद:

  1. रूबी कुछ नामकरण सम्मेलनों लागू करता है। रूबी में प्रतीकों के प्रश्न चिह्न नहीं हो सकते हैं। इस प्रकार :my_boolean_attribute? दोनों के आमंत्रण NameError के साथ विफल हो जाएंगे। संपादित करें: सही नहीं, केवल प्रतीक के लिए उद्धृत वाक्यविन्यास का उपयोग करें, उदाहरण के लिए, :"my_attribute?"
  2. प्रतीक अपरिवर्तनीय हैं, किसी को असाइन करने का प्रयास करने से SyntaxError फेंक दिया जाएगा।
+6

रूबीस्ट आमतौर पर is_ उपसर्ग का उपयोग नहीं करता है न तो परिवर्तनीय नामों में और न ही विधि नामों में। बस कमाल? is_awesome के बजाय? –

+0

अच्छा बिंदु, weppos। उलझन में आने से बचने के लिए 'is_' संपादित किया गया ;-) –

+0

इस उत्तर से मैं इकट्ठा करता हूं कि असली सम्मेलन नहीं है? :/ –

5

? विधि नामों के लिए सम्मेलन है, चर नहीं। आप @foo? नामक एक इंस्टेंस वैरिएबल का उपयोग नहीं कर सकते हैं, हालांकि आप @foo नामक एक चर का उपयोग कर सकते हैं और यदि आप चाहें तो मैन्युअल रूप से बनाए गए गेटटर विधि foo? का नाम दे सकते हैं।

+0

हम्म के लिए अलियासिंग उपयोग करने के लिए है, इसलिए attr_accessor:

ओह, और लगभग अनिवार्य लिंक शामिल करना भूल सहायक 'पट्टी' नहीं पड़ेगा मेरे लिए अंत से दूर हुह। उदाहरण के लिए यह वास्तव में सम्मेलन नहीं सुनना खुशी हुई। सोचा था कि मैं पागल हो रहा था। प्रतीक पकड़ के लिए –

6

attr_accessor प्रतीक का तात्पर्य है कि चर नाम @my_boolean_attribute है, इसलिए कि तुम क्या की स्थापना किया जाना चाहिए (प्रतीक नहीं) है।

इसके अलावा, आप इसका उपयोग नहीं कर सकते? चर के लिए, बस विधि नाम।

+0

ty। self.my_boolean_attribute सही काम करेगा? –

+0

हाँ, यह चाहिए। –

+0

ओह, मुझे जोड़ने दो - केवल उदाहरण के तरीकों के भीतर। कक्षा के दायरे में यह एक वर्ग-स्कोप चर (@@ my_boolean_attribute) की तलाश करेगा। ऐसा नहीं है कि मुझे आपको बताने की ज़रूरत है, लेकिन मैं यह सुनिश्चित करना चाहता था कि मैंने जो कहा वह तकनीकी रूप से सही था। –

3

बंदर-पैचिंग metaprogramming - हो सकता है इसे और अधिक सुंदर बनाया जा सकता है, यह केवल एक त्वरित मसौदा है, और मैं थोड़ी देर के लिए metaprogramming नहीं किया है ...

# inject the convenience method into the definition of the Object class 
class Object 
    def Object::bool_attr(attrname) 
    class_eval { define_method(attrname.to_s, 
      lambda { instance_variable_get('@' + attrname.to_s.chop) }) } 
    class_eval { define_method(attrname.to_s.chop+"=", 
      lambda { |x| instance_variable_set('@'+attrname.to_s.chop, x) }) } 
    end 
end 

### somewhere later 

class MyClass 

    bool_attr :my_boolean_attribute? 

    def initialize 
    @my_boolean_attribute = true 
    end 
end 

# yet even more later 

foo = MyClass.new 
bar = MyClass.new 

foo.my_boolean_attribute = 1 
puts foo.my_boolean_attribute? 
puts bar.my_boolean_attribute? 
इस दृष्टिकोण के साथ

, आप DRY हो सकते हैं और अच्छा प्रश्न भी प्राप्त कर सकते हैं। आपको "bool_attr" से बेहतर नाम चुनने की आवश्यकता हो सकती है, जैसे, "bool_attr_accessor" या कुछ समान।

मैंने जो परिभाषाएं की हैं, वे थोड़ी क्रैकी हैं, इस अर्थ में कि मूल चिह्न में प्रश्न चिह्न मौजूद है। शायद एक क्लीनर दृष्टिकोण प्रतीक नाम में प्रश्नचिह्न से बचने और विधि की परिभाषा के दौरान इसे जोड़ने के लिए होगा - कम भ्रमित होना चाहिए। Seeing metaclasses clearly

+0

+1! संभवतः इस मामले में सुविधा विधि नहीं जोड़नी चाहिए क्योंकि यह सम्मेलन नहीं है। मैं दूसरों को भ्रमित नहीं करना चाहता हूं। यद्यपि अन्य समस्याओं से विचारों को खुशी से कैनबलाइज किया जाएगा! –

+1

यदि आप इसे किसी टीम में बनाए रखते हैं, तो मुझे लगता है कि इस तरह के प्रश्नों पर समीक्षाओं पर विचार-विमर्श किया जाना चाहिए - कुछ स्थितियों में यह समझ में आ सकता है, कुछ परिदृश्यों में यह नहीं होगा। मैंने रूबी को एक टीम में कोड नहीं किया, इसलिए मुझे एक ऐसे दृष्टिकोण के लिए जाना पड़ता है जो मुझे कम से कम एलओसी देखने के लिए देता है। –

+0

+1। अगर केवल मेटा-चतुरता के लिए ... –

38

सबसे आसान तरीका है जल्दी से एक "सवाल विधि" जोड़ने के लिए अपने पाठक विधि

class Foo 
    attr_accessor :dead 
    alias_method :dead?, :dead # will pick up the reader method 
end 
+0

कमाल! मैं इसे लंबा हाथ कर रहा था। –

+0

इसका उपयोग करके आप 'मृत' और 'मृत' दोनों का उपयोग कर सकते हैं, है ना? लेकिन केवल 'मृत' के माध्यम से सेटिंग की अनुमति देता है? –

+3

सेटिंग "मृत =" के माध्यम से रहती है – Julik

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