Home > Back-end >  How do I create an alternative constructor using a class method?
How do I create an alternative constructor using a class method?

Time:12-26

The following code should generate an Employee instance from an employee string but doesn't seem to work. The instance is not created. How do I make it work?

class Employee:
    def __init__(self,first,last,pay):
        self.first=first
        self.last=last
        self.pay=pay
    def pay_increase(self):
        self.pay  = (self.pay * 0.1)
    def emp_str(self,emp_str):
        first , last , pay = emp_str.split('-')
        
emp1=Employee('reza','azaf',2000)
emp1.pay_increase()

emp2_str= 'rezd-454-454'
emp2 = Employee.emp_str(emp2_str)
print(emp2.first)

CodePudding user response:

You expect emp_str to return na emp2, but it returns nothing. Add: return Employee(first, last, pay)

Another issue, you call emp_str on class, so it should be an static method.

CodePudding user response:

Try this:

class Employee:

    def __init__(self, first=None, last=None, pay=None):
        self.first = first
        self.last = last
        self.pay = pay

    def pay_increase(self):
        self.pay  = (self.pay * 0.1)

    def emp_str(self,emp_str): 
        first, last, pay = emp_str.split('-')
        self.first = first

emp1 = Employee(first='reza',last='azaf',pay=2000) 
emp1.pay_increase()

emp2_str = 'rezd-454-454'

emp2 = Employee()
emp2.emp_str(emp2_str)

print(emp2.first)

CodePudding user response:

I'm no quite sure what is the thing you want, but it looks to me you want your emp_str to be an alternative constructor given your example and tags.

For that we use the classmethod decorator and build the method accordingly

class Employee:

    def __init__(self,first,last,pay):
        self.first=first
        self.last=last
        self.pay=pay
        
    def pay_increase(self):
        self.pay  = (self.pay * 0.1)
        
    @classmethod    
    def emp_str(cls,emp_str):
        first , last , pay = emp_str.split('-')
        return cls(first , last , int(pay))

    def __str__(self):#lets also add a way to nicely print this object
        return f"{type(self).__name__}({self.first!r}, {self.last!r}, {self.pay!r})"
        

and now quickly test it

>>> emp1=Employee('reza','azaf',2000)
>>> print(emp1)
Employee('reza', 'azaf', 2000)
>>> emp1.pay_increase()
>>> print(emp1)
Employee('reza', 'azaf', 2200.0)
>>> emp2_str= 'rezd-454-454'
>>> emp2 = Employee.emp_str(emp2_str)
>>> print(emp2)
Employee('rezd', '454', 454)
>>> print(emp2.first)
rezd
>>> 

CodePudding user response:

emp_str needs to be a classmethod and return the newly created class like so:

@classmethod
def emp_str(cls,emp_str):
    first , last , pay = emp_str.split('-')
    return cls(first,last,pay)

Per your request, without a class method:

def emp_str(emp_str):
    first , last , pay = emp_str.split('-')
    return Employee(first, last, pay)

Make sure it is outside of the class.

  • Related