Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Python construct child class from parent

I am quite new with python, is there a way to construct a child class using a parent instance?

Well I was thinking about:

class A:
  def __init__(self,a,b):
     self.a = a
     self.b = b         

class B(A):
  def __init__(self,A):
    self.super = A
    self.c = -1

  def __init__(self,a,b,c):
    super(a,b)
    self.c = c

myA = A(1,2)
myB = B(myA)

So for having B objects I could use A objects to construct them.

like image 342
dijkstraman Avatar asked Jul 23 '14 21:07

dijkstraman


1 Answers

This will do what you ask, and create a new B, using the data from an existing A, and then complete the initialisation of the new B:

class A(object):
    def __init__(self, a, b):
        self.a = a
        self.b = b

    def __str__(self):
        return "A: a = %s, b = %s" % (self.a, self.b)

class B(A):
    def __init__(self, *args):
        if type(args[0]) is A:
            self.__dict__ = args[0].__dict__.copy()
            c = args[1]
        else:
            super(B, self).__init__(*args[:2])
            c = args[2]
        self.c = c

    def __str__(self):
        return "B: a = %s, b = %s, c = %s" % (self.a, self.b, self.c)

Usage:

myA = A(1, 2)
print myA
print B(3,4,5)   # regular B
myB = B(myA, 10) # B created from an A
print myB

Output:

A: a = 1, b = 2
B: a = 3, b = 4, c = 5
B: a = 1, b = 2, c = 10

Note that the new instance doesn't get a new copy of the data, it gets a new set of references to that data. If a were a list and you did myA.a.append(value), then myB.a would also have value in it. If you want that not to be the case, change the assignment of __dict__ to:

self.__dict__ = deepcopy(args[0].__dict__)

Note: None of this won't work if you're using slots, because __dict__ won't exist

like image 138
Jamie Cockburn Avatar answered Oct 03 '22 07:10

Jamie Cockburn