python - पायथन में स्टेटिक तरीके?




static-methods (6)

पायथन में स्टेटिक तरीके?

क्या पाइथन में स्थैतिक तरीकों के लिए संभव है ताकि मैं उन्हें कक्षा शुरू किए बिना कॉल कर सकूं, जैसे:

ClassName.StaticMethod()

हां, स्थिर तरीकों को इस तरह बनाया जा सकता है (हालांकि यह विधियों के लिए CamelCase के बजाय अंडरस्कोर का उपयोग करने के लिए थोड़ा और Pythonic है):

class ClassName(object):

    @staticmethod
    def static_method(kwarg1=None):
        '''return a value that is a function of kwarg1'''

उपरोक्त सजावटी वाक्यविन्यास का उपयोग करता है। यह वाक्यविन्यास बराबर है

class ClassName(object):

    def static_method(kwarg1=None):
        '''return a value that is a function of kwarg1'''

    static_method = staticmethod(static_method)

जैसा कि आपने वर्णन किया है इसका उपयोग किया जा सकता है:

ClassName.static_method()

एक स्थिर विधि का एक अंतर्निहित उदाहरण पायथन 3 में str.maketrans() है, जो पायथन 2 में string मॉड्यूल में एक फ़ंक्शन था।

आपके द्वारा वर्णन किए जाने वाले एक और विकल्प का उपयोग classmethod , अंतर यह है कि क्लासमेड क्लास को एक निहित पहला तर्क के रूप में प्राप्त करता है, और यदि उप-वर्गीकृत होता है, तो यह सबक्लास को पहले तर्क के रूप में प्राप्त करता है।

class ClassName(object):

    @classmethod
    def class_method(cls, kwarg1=None):
        '''return a value that is a function of the class and kwarg1'''

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

इन्हें आमतौर पर वैकल्पिक कन्स्ट्रक्टर के रूप में उपयोग किया जाता है।

new_instance = ClassName.class_method()

एक अंतर्निहित उदाहरण dict.fromkeys() :

new_dict = dict.fromkeys(['key1', 'key2'])

क्या पाइथन में स्थैतिक तरीकों के लिए संभव है ताकि मैं उन्हें कक्षा शुरू किए बिना कॉल कर सकूं, जैसे:

ClassName.StaticMethod ( )

आपको वास्तव में @staticmethod सजावट का उपयोग करने की आवश्यकता नहीं है। बस एक विधि घोषित करें (जो स्वयं पैरामीटर की अपेक्षा नहीं करता है) और इसे कक्षा से कॉल करें। सजावट केवल तभी होता है जब आप इसे किसी उदाहरण से कॉल करने में सक्षम होना चाहते हैं (जो आप नहीं करना चाहते थे)

अधिकतर, आप केवल कार्यों का उपयोग करते हैं ...


मुझे समय-समय पर यह सवाल आती है। उपयोग का मामला और उदाहरण जो मुझे पसंद है:

[email protected]:/home/jeffs  $ python36
Python 3.6.1 (default, Sep  7 2017, 16:36:03) 
[GCC 6.3.0 20170406] on linux
Type "help", "copyright", "credits" or "license" for more information.
>>> import cmath
>>> print(cmath.sqrt(-4))
2j
>>>
>>> dir(cmath)
['__doc__', '__file__', '__loader__', '__name__', '__package__', '__spec__', 'acos', 'acosh', 'asin', 'asinh', 'atan', 'atanh', 'cos', 'cosh', 'e', 'exp', 'inf', 'infj', 'isclose', 'isfinite', 'isinf', 'isnan', 'log', 'log10', 'nan', 'nanj', 'phase', 'pi', 'polar', 'rect', 'sin', 'sinh', 'sqrt', 'tan', 'tanh', 'tau']
>>> 

कक्षा cmath की वस्तु बनाने के लिए यह समझ में नहीं आता है, क्योंकि cmath ऑब्जेक्ट में कोई स्थिति नहीं है। हालांकि, cmath विधियों का एक संग्रह है जो सभी किसी भी तरह से संबंधित हैं। ऊपर दिए गए मेरे उदाहरण में, सीएमएथ में सभी कार्यों को जटिल संख्याओं पर कुछ तरीकों से कार्य करना है।


शायद सबसे आसान विकल्प सिर्फ उन कार्यों को कक्षा के बाहर रखना है:

class Dog(object):
    def __init__(self, name):
        self.name = name

    def bark(self):
        if self.name == "Doggy":
            return barking_sound()
        else:
            return "yip yip"

def barking_sound():
    return "woof woof"

इस विधि का उपयोग करते हुए, आंतरिक ऑब्जेक्ट स्थिति (साइड इफेक्ट्स) को संशोधित या उपयोग करने वाले फ़ंक्शंस को कक्षा में रखा जा सकता है, और पुन: प्रयोज्य उपयोगिता कार्यों को बाहर ले जाया जा सकता है।

मान लें कि इस फ़ाइल को dogs.py कहा जाता है। इनका उपयोग करने के लिए, आप dogs.barking_sound() बजाय dogs.barking_sound() कॉल dogs.Dog.barking_sounddogs.Dog.barking_sound

यदि आपको कक्षा का हिस्सा बनने के लिए वास्तव में एक स्थिर विधि की आवश्यकता है, तो आप staticmethod सजावट का उपयोग कर सकते हैं।


हां, staticmethod सजावट का उपयोग कर

class MyClass(object):
    @staticmethod
    def the_static_method(x):
        print x

MyClass.the_static_method(2) # outputs 2

ध्यान दें कि कुछ कोड एक सजावटी के बजाय फ़ंक्शन के रूप में staticmethod का उपयोग करके एक स्थिर विधि को परिभाषित करने की पुरानी विधि का उपयोग कर सकते हैं। इसका उपयोग केवल तभी किया जाना चाहिए यदि आपको पायथन (2.2 और 2.3) के प्राचीन संस्करणों का समर्थन करना है

class MyClass(object):
    def the_static_method(x):
        print x
    the_static_method = staticmethod(the_static_method)

MyClass.the_static_method(2) # outputs 2

यह पूरी तरह से पहले उदाहरण ( @staticmethod का उपयोग करके) के समान है, बस अच्छे सजावटी वाक्यविन्यास का उपयोग नहीं कर रहा है

अंत में, staticmethod कम से कम उपयोग करें! ऐसी कुछ स्थितियां हैं जहां पायथन में स्थिर-विधियां आवश्यक हैं, और मैंने उन्हें कई बार उपयोग किया है जहां एक अलग "शीर्ष-स्तरीय" फ़ंक्शन स्पष्ट होगा।

staticmethod :

एक स्थैतिक विधि को एक निहित पहला तर्क प्राप्त नहीं होता है। एक स्थिर विधि घोषित करने के लिए, इस मुहावरे का उपयोग करें:

class C:
    @staticmethod
    def f(arg1, arg2, ...): ...

@staticmethod फॉर्म एक फ़ंक्शन decorator - विवरण के लिए फ़ंक्शन परिभाषाओं में फ़ंक्शन परिभाषाओं का विवरण देखें।

इसे कक्षा में (जैसे Cf() ) या उदाहरण पर (जैसे C().f() ) कहा जा सकता है। उदाहरण को कक्षा के अलावा अनदेखा किया जाता है।

पायथन में स्टेटिक विधियां जावा या सी ++ में पाए गए समान हैं। एक और उन्नत अवधारणा के लिए, classmethod() देखें।

स्थिर तरीकों के बारे में अधिक जानकारी के लिए, मानक प्रकार पदानुक्रम में मानक प्रकार पदानुक्रम पर दस्तावेज़ों से परामर्श लें।

संस्करण 2.2 में नया।

संस्करण 2.4 में बदल गया: समारोह सजावट वाक्यविन्यास जोड़ा गया।


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

# garden.py
def trim(a):
    pass

def strip(a):
    pass

def bunch(a, b):
    pass

def _foo(foo):
    pass

class powertools(object):
    """
    Provides much regarded gardening power tools.
    """
    @staticmethod
    def answer_to_the_ultimate_question_of_life_the_universe_and_everything():
        return 42

    @staticmethod
    def random():
        return 13

    @staticmethod
    def promise():
        return True

def _bar(baz, quux):
    pass

class _Dice(object):
    pass

class _6d(_Dice):
    pass

class _12d(_Dice):
    pass

class _Smarter:
    pass

class _MagicalPonies:
    pass

class _Samurai:
    pass

class Foo(_6d, _Samurai):
    pass

class Bar(_12d, _Smarter, _MagicalPonies):
    pass

...

# tests.py
import unittest
import garden

class GardenTests(unittest.TestCase):
    pass

class PowertoolsTests(unittest.TestCase):
    pass

class FooTests(unittest.TestCase):
    pass

class BarTests(unittest.TestCase):
    pass

...

# interactive.py
from garden import trim, bunch, Foo

f = trim(Foo())
bunch(f, Foo())

...

# my_garden.py
import garden
from garden import powertools

class _Cowboy(garden._Samurai):
    def hit():
        return powertools.promise() and powertools.random() or 0

class Foo(_Cowboy, garden.Foo):
    pass

यह अब थोड़ा और सहज ज्ञान युक्त और स्वयं-दस्तावेज बन गया है जिसमें संदर्भ कुछ घटकों का उपयोग किया जाता है और यह अलग-अलग परीक्षण मामलों का नामकरण करने के लिए आदर्श रूप से बाहर निकलता है और साथ ही साथ शुद्ध मॉड्यूल के परीक्षण के तहत वास्तविक मॉड्यूल के परीक्षण के तरीके के बारे में एक सीधा दृष्टिकोण है। ।

मुझे अक्सर परियोजना के उपयोगिता कोड को व्यवस्थित करने के लिए इस दृष्टिकोण को लागू करने के लिए व्यवहार्य लगता है। अक्सर, लोग तुरंत उछालते हैं और एक utils पैकेज बनाते हैं और 9 मॉड्यूल के साथ समाप्त होते हैं जिनमें से एक में 120 एलओसी होता है और बाकी दो दर्जन एलओसी होते हैं। मैं इसके साथ शुरू करना पसंद करता हूं और इसे एक पैकेज में परिवर्तित करता हूं और केवल उन जानवरों के लिए मॉड्यूल बनाता हूं जो वास्तव में उनके लायक हैं:

# utils.py
class socket(object):
    @staticmethod
    def check_if_port_available(port):
        pass

    @staticmethod
    def get_free_port(port)
        pass

class image(object):
    @staticmethod
    def to_rgb(image):
        pass

    @staticmethod
    def to_cmyk(image):
        pass




static-methods