اذهب إلى المحتوى

السؤال

نشر

هذا مثال لشيفرة برمجية لصنف مكتوب بالبايثون:

class MyClass(object):
    ...
    def get_my_attr(self):
        ...

    def set_my_attr(self, value):
        ...

وهذا نفس المثال لكن باستخدام @property:

class MyClass(object):
    ...        
    @property
    def my_attr(self):
        ...

    @my_attr.setter
    def my_attr(self, value):
        ...

كما ترون فإن البايثون تسمح لنا باستخدام الطريقتين فأي الطريقتين أفضل ولماذا ؟

Recommended Posts

  • 0
نشر

أنصحك باستخدام الخصائص (properties)، لأن جميع السمات (attributes) عامة في البايثون، لذلك إذا قمت بإضافة خط سفلي (_) إلى الأسماء  فهو سيبقى مجرد تفصيل محدد لتلك السمة والتي قد لا تبقى نفسها في الإصدارات التالية من الشيفرة البرمجية، وهو لا يمنعك من الحصول على معلومات (getting) أو تعيين (setting) لتلك السمة، ولذلك فإن سمات الوصول القياسية (standard attribute access) هي الطريقة العادية (في البايثون) للوصول إلى السمات (أقصد طريقة المثال الثاني).
ومن المميزات الأخرى للخصائص أنها متطابقة صياغيا مع سمات الوصول، لذلك يمكنك تغييرها دون أن تقوم بأي تعديلات على الشيفرة البرمجية للعميل.

المصدر

  • 0
نشر

عليك أولًا التعرّف عليها. بدايةً، يجب أن تعلم  أنه يمكن استخدامها كداالة أو كمُزخرف decorator لتحويل تابع إلى خاصيّة.

تعيد الدالة property()‎ خاصيّة يُمكن التحكم بها (خاصيّة مُدارة -property object-) لها تابع للحصول على قيمتها، وتابع تعيين قيمة لها، وتابع حذف قيمتها، ولها سلسلة توثيق (docstring) خاصّة بها (الكائن المُعاد يحتوي على الخاصيّات fget، وfset، وfdel التي تمثّل الدوال الممررة).

لها البنية التالية:

property(fget=None, fset=None, fdel=None, doc=None)

fget الدالّة التّي ستُستخدم للحصول على قيمة الخاصيّة.
fset الدالّة التّي ستُستخدم لتعيين قيمة للخاصيّة.
fdel الدالّة التّي ستُستخدم لحذف قيمة الخاصيّة.
doc سلسلة توثيق الخاصيّة.

مثال:

class C:
    def __init__(self):
        self._x = None
    def getx(self):
        return self._x
    def setx(self, value):
        self._x = value
    def delx(self):
        del self._x
	# إنشاء الخاصيّة
    x = property(getx, setx, delx, "The 'x' property.")

الكائن c نسخة من الصنف C، فالجملة ‎c‎.‎x‎ ستستدعي دالة الحصول على القيمة، و‎c‎.‎x ‎=‎ ‎value ستستدعي دالة ضبط القيمة، و‎del‎ ‎c‎.‎x‎ ستستدعي دالة حذف قيمة الخاصيّة.

إن أُعطِيَت قيمة للمعامل doc، فستكون قيمته هي سلسلة توثيق الخاصيّة. أما إن لم تمرر قيمة للمعامل، فستنسخ الخاصيّة سلسلة توثيق الدالة fget (إن كانت موجودة). ما يسمح بإنشاء خاصيّات قابلة للقراءة فقط (read-only) باستخدام الدالة property()‎ كمُزخرف:

class Parrot:
    def __init__(self):
        self._voltage = 100000
    @property
    def voltage(self):
        """الحصول على قيمة الجهد الحاليّة"""
        return self._voltage

يحوّل المُزخرِف ‎@‎property الدالةvoltage()‎ إلى دالة تحصل على قيمة الخاصيّة ذات نفس الاسم، وتكون سلسلة التوثيق الخاصة بالخاصيّة voltage هي السلسلة "الحصول على قيمة الجهد الحالية". ما يعني بأنك تستطيع الحصول على قيمة الخاصية voltage كما يلي (لاحظ أننا لم نستدعي الدالة voltage()‎):

p = Parrot()
p.voltage
# 100000


كائن الخاصية يحتوي على الدالة getter للحصول على القيمة والدالة setter لضبط قيمة للخاصية وdeleter لحذف قيمة الخاصية، ويمكن استخدام هذه الدوال كمُزخرِفات تُنشئ نسخة من الخاصية ذات دوال مُتحكّمة تتمثل في الدوال المُزخرَفة.

كما ترى فإن استخدامها يمنحنا الكثير من الميزات التحكمية، إضافةً إلى ذلك يجب أن تلاحظ أنها تجعل استخدام getter و setter أسهل بكثير في البرمجة الموجهة للكائنات.

انضم إلى النقاش

يمكنك أن تنشر الآن وتسجل لاحقًا. إذا كان لديك حساب، فسجل الدخول الآن لتنشر باسم حسابك.

زائر
أجب على هذا السؤال...

×   لقد أضفت محتوى بخط أو تنسيق مختلف.   Restore formatting

  Only 75 emoji are allowed.

×   Your link has been automatically embedded.   Display as a link instead

×   جرى استعادة المحتوى السابق..   امسح المحرر

×   You cannot paste images directly. Upload or insert images from URL.

  • إعلانات

  • تابعنا على



×
×
  • أضف...