2011-06-01 26 views
39

मैं ऑब्जेक्ट ओरिएंटेड प्रोग्रामिंग पर और के रूप में मैं कैसे वर्ग की व्याख्या करने पर brushing कर रहा हूँ एक अजगर कक्षा को पढ़ा रहा हूँ, मैं एक खाली वर्ग परिभाषा देखा इस वर्ग का एक उद्देश्य के लिए एक नाम और अन्य विशेषताओं को परिभाषित करने के:अजगर खाली वर्ग वस्तु

john = Employee() 
john.full_name = "john doe" 

दिलचस्प!

मुझे आश्चर्य है कि इस तरह की कक्षा के लिए गतिशील रूप से परिभाषित करने का कोई तरीका है या नहीं? कुछ ऐसा:

john.greet() = print 'hello world!' 

यह मेरे पायथन दुभाषिया में काम नहीं करता है लेकिन क्या ऐसा करने का दूसरा तरीका है?

+1

संभव है? हाँ। एक अच्छा विचार? शायद ही (कुछ मेटाप्रोग्रामिंग के बाहर, ज़ाहिर है)। – delnan

+3

मैंने देखा है कि सबसे छोटी खाली कक्षा परिभाषा http://www.gossamer-threads.com/lists/python/python/832915#832915 से है: 'कर्मचारी = प्रकार ('कर्मचारी',(), {})' और फिर 'जॉन = कर्मचारी() 'आदि – eudoxos

उत्तर

30

एक वर्ग और अधिक या कम वस्तुओं के लिए विशेषताओं का एक dict के लिए एक फैंसी आवरण है जब आप एक वर्ग का दृष्टांत। आप उसके गुण को असाइन कर सकते हैं, और उन foo.__dict__ में संग्रहीत किया जाएगा; इसी तरह, आप किसी भी गुण आप पहले से ही लिखा है के लिए foo.__dict__ में देख सकते हैं

इसका मतलब है आप जैसे कुछ साफ गतिशील कर सकते हैं:

class Employee: pass 
def foo(self): pass 
Employee.foo = foo 

साथ ही साथ एक विशेष उदाहरण को असाइन करना। (संपादित करें: self पैरामीटर जोड़ा)

+7

आपका उदाहरण इरादे से काम नहीं करेगा: 'john.foo() '' TypeError' बढ़ाएगा, क्योंकि कोई' self' पैरामीटर 'नहीं है। किसी वर्ग पर फ़ंक्शन डालने से इसे एक विधि में बदल दिया जाता है, इसलिए इसे 'स्वयं' लेना होगा। दूसरी तरफ, यदि आप किसी फ़ंक्शन को फ़ंक्शन असाइन करते हैं, तो यह एक फ़ंक्शन बनी हुई है और इसका उदाहरण 'self'' तक पहुंच नहीं है, जो आमतौर पर उपयोगी नहीं होता है। –

+0

@ जोचेन: आप निश्चित रूप से सही हैं। टा! ओपी को: अगर आप समझते हैं कि क्या गलत हुआ और यह क्यों ठीक हो जाता है तो यह शायद मदद करेगा! – katrielalex

+0

@ जोकन, इस पर कुछ रंग जोड़ने के लिए धन्यवाद। यदि कार्य परिभाषित किया गया है तो केवल 'विशिष्ट' तक पहुंच कितनी महत्वपूर्ण/उपयोगी है (केवल मुझे लगता है)। दूसरे शब्दों में, इस फ़ंक्शन को कर्मचारी प्रकार के सभी ऑब्जेक्ट्स के लिए परिभाषित नहीं किया जा रहा है (जब तक कि आप @ कैटरीलेलेक्स के उदाहरण का उपयोग न करें और क्लासनाम का उपयोग करके इसे परिभाषित करें), लेकिन केवल कक्षा के उदाहरण के लिए (जैसे ओपी में मेरे "जॉन" उदाहरण में) – Ramy

15

lambda साथ प्रयास करें:

john.greet() 

संपादित:

john.greet = lambda : print('hello world!') 

, जिसे आप ऐसा करने में सक्षम हो जाएगा धन्यवाद थॉमस कश्मीर टिप्पणी के लिए - इस पर काम करता है Python 3.2 और पायथन 2 के लिए नहीं, जहां printstatement प्रतीत होता है । लेकिन इस, lambda रों के लिए काम करेंगे बयान बिना (दाएं क्षमा करें, मैं जानता हूँ कि केवल python3.2 (?)

+1

यह वास्तव में काम नहीं करता है: लैम्ब्डा में बयान शामिल नहीं हो सकते हैं। – katrielalex

+0

@ katrielalex - मेरे पायथन 3.2 पर बिल्कुल सही काम करता है (निश्चित रूप से 'प्रिंट' के लिए जोड़े गए कोष्ठक के साथ)। क्या राज्यपाल? –

+0

प्री पायथन 3.x में काम नहीं करता है स्पष्ट रूप से – Ramy

0

आप AttrDict इस्तेमाल कर सकते हैं

>>> from attrdict import AttrDict 
>>> my_object = AttrDict() 
>>> my_object.my_attribute = 'blah' 
>>> print my_object.my_attribute 
blah 
>>> 

PyPI से attrdict स्थापित करें: भी

pip install attrdict 

यह अन्य स्थितियों में उपयोगी है - जैसे कि जब आप dict कुंजी का उपयोग करने के गुण की जरूरत है ।

0

आप collection मानक मॉड्यूल से "नामित टुपल्स" का भी उपयोग कर सकते हैं। नामांकित tuples "साधारण" tuples की तरह काम करते हैं लेकिन तत्वों के नाम हैं और आप "डॉट वाक्यविन्यास" का उपयोग कर तत्वों तक पहुंच सकते हैं। collection docs से:

>>> # Basic example 
>>> Point = namedtuple('Point', ['x', 'y']) 
>>> p = Point(11, y=22)  # instantiate with positional or keyword arguments 
>>> p[0] + p[1]    # indexable like the plain tuple (11, 22) 
33 
>>> x, y = p    # unpack like a regular tuple 
>>> x, y 
(11, 22) 
>>> p.x + p.y    # fields also accessible by name 
33 
>>> p      # readable __repr__ with a name=value style 
Point(x=11, y=22) 
संबंधित मुद्दे