2

lets say we have class A and it has one instance - x. How to make a child class of class A where I would be able to pass x as an argument and get all its parameters and pass it to child class object. precisely speaking I want to do something like this.

class A:
    def __init__(self, parameter1, parameter2):
        self.parameter1 = parameter1
        self.parameter2 = parameter2




class B(A):
    def __init__(self, Ainstance, someParameter):
        super().__init__(**Ainstance.__dict__)
        self.someParameter = someParameter

x = A(parameter1='1', parameter2='2')

x = B(x, someParameter='3')

print(x.parameter1)
print(x.parameter2)
print(x.someParameter)

the goal is to create a class where I would be able to get all the parameters of parent class object, and add my own attributes. The problem in the code above is I won't be able to do that with all classes because not all of them has __dict__ attribute.

  • 1
    1. You don't have to do it with all classes, only with class A, as you pass an A-instance? 2. Why are you doing this? Ask a question on how to solve THAT problem. This way is probably not it. – Lennart Regebro Sep 24 '21 at 11:11
  • While you can technically do it, I don't see why we want to do this, though? What's the reasoning behind this? – dswij Sep 24 '21 at 11:13
  • The problem is there is no class A, there is a library class. I just wanted to create the exact same object but with some additional attributes. But I can't add attributes to the library class. OOP is still complicating thing for me so I wanted to solve my problem this way, But by the looks of it, this was not appropriate way. – Nika Metreveli Sep 24 '21 at 12:49
  • A library class? Did you mean that you just want to derive from it? – quamrana Sep 24 '21 at 12:51
  • Not quite. I want to use instance of a library class as an argument to pass its parameters to a child class object. so I will have the exact same object, with additional attributes and methods. To be more precise I use socket class of socket library. and when new client connects I am given a client object and using this client object I want to create a new object but with username, address associated with socket and other attributes/methods. – Nika Metreveli Sep 24 '21 at 13:13
  • Could you just add those attributes to the socket? – quamrana Sep 24 '21 at 13:45
  • No I couldn't. I get this error while doing so: AttributeError: 'socket' object has no attribute 'username' – Nika Metreveli Sep 24 '21 at 13:55
  • Yes I did exactly that, I even tried setattr(server_socket, 'username', 'some username') and both gave the same error. I don't know what's wrong. I guess another subject to search up. – Nika Metreveli Sep 24 '21 at 14:06
  • See my answer about using a `proxy` pattern in python. – quamrana Sep 24 '21 at 14:07

2 Answers2

2

I have this example code which I use to remind myself how to construct a proxy.

#soProxyPattern

class Example:
    def __init__(self):
        self.tag_name = 'name'
    def foo(self):
        return 'foo'
    def bar(self, param):
        return param
    
class Container:
    def __init__(self, contained):
        self.contained = contained
        self.user_name = 'username'

    def zoo(self):
        return 0
    
    def __getattr__(self, item):
        if hasattr(self.contained, item):
            return getattr(self.contained,item)
        #raise item

c = Container(Example())
print(c.zoo())
print(c.foo())
print(c.bar('BAR'))
print(c.tag_name)
print(c.user_name)

The output is:

0
foo
BAR
name
username

This shows that Container can have its own attributes (methods or variables) which you can access over and above all of the attributes of the contained instance.

quamrana
  • 37,849
  • 12
  • 53
  • 71
1

Instead of dict you could use the dir and getattr like this:

class A:
    def __init__(self, parameter1, parameter2):
        self.parameter1 = parameter1
        self.parameter2 = parameter2


 class B(A):
     def __init__(self, Ainstance, someParameter):
        parameters = {param: getattr(Ainstance, param) for param in dir(Ainstance) if not param.startswith("__")} 
        super().__init__(**parameters)
        self.someParameter = someParameter

For a more detailed explanation see: Get all object attributes in Python?

RVA92
  • 666
  • 4
  • 17