How to set a python property in __init__

24,004

Solution 1

I do not see any real problem with your code. In __init__, the class is fully created and thus the properties accessible.

Solution 2

class STransaction(object):
    """A statement transaction"""
    def __init__(self, date):
        self._date = None #1
        self.date = date  #2

If you want to set the proxy field self._date without executing of your setter use the #1 line. If you would like to execute the setter at startup too use the #2. Both ways are correct, it's just a matter of what do you want to do.

Share:
24,004
Aaron Barclay
Author by

Aaron Barclay

Updated on March 24, 2021

Comments

  • Aaron Barclay
    Aaron Barclay about 3 years

    I have a class with an attribute I wish to turn into a property, but this attribute is set within __init__. Not sure how this should be done. Without setting the property in __init__ this is easy and works well

    import datetime
    
    class STransaction(object):
        """A statement transaction"""
        def __init__(self):
            self._date = None
    
        @property
        def date(self):
            return self._date
    
        @date.setter
        def date(self, value):
            d = datetime.datetime.strptime(value, "%d-%b-%y")
            self._date = d
    
    st = STransaction()
    st.date = "20-Jan-10"
    

    But once initialization needs to occur in __init__ it gets more complicated and I am not sure of the correct course of action.

    class STransaction(object):
        """A statement transaction"""
        def __init__(self, date):
            self._date = None
    

    Strangely to me, the following seems to work but smells very bad.

    class STransaction(object):
        """A statement transaction"""
        def __init__(self, date):
            self._date = None
            self.date = date
    
        @property
        def date(self):
            return self._date
    
        @date.setter
        def date(self, value):
            d = datetime.datetime.strptime(value, "%d-%b-%y")
            self._date = d
    

    What is the correct way to go about setting properties in __init__?

    Thanks, Aaron.

  • Aaron Barclay
    Aaron Barclay over 13 years
    Ok, so perhaps I am looking at this the wrong way. At the point of init is the property already created so my call to self.date is accessing via the property is the same way that my call to st.date is?
  • Florian Mayer
    Florian Mayer over 13 years
    Yes, exactly (why does Stackoverflow dislike short, to-the-point messages? - it refused to post just "Yes, exactly").
  • ThR37
    ThR37 over 13 years
    +1 Perfectly right. I would add that the self._date = None in init is really useless in this code (You can in some cases put the initialization of properties hidden variables in the getter using RAII ( if not hasattr(self,_smth): do initialization...)
  • Nas Banov
    Nas Banov over 11 years
    Why would you want to set _date to None when init clearly is called with some particular date? You should store the correct value, hence #1 is not viable.