You haven't really said what the syntax you want is supposed to accomplish which would be useful to know...
Nesting classes as shown below would allow you to achieve the syntax you want, but the result is not only very "unpythonic" — it's also completely useless and I can't think a reasonable way to implement to change that.
Without more information about what you're doing, at the moment I can think of an alternative to suggest. I suggest you just create a bunch of regular non-nested classes and explicitly instantiate them when needed.
Note that I've changed the names you were to follow the PEP 8 naming conventions.
class Company:
def __init__(self, name):
self.name = name
class Department:
def __init__(self, dept_name):
self.dept_name = dept_name
class Employee:
def __init__(self, given_name):
self.given_name = given_name
Company('MS').Department('Finance').Employee('John').full_name = 'John MacDonalds'
Here's a way to implement your tree structure via Python "autovivification" using the Vividict
dictionary defined in this answer.
I've adapted it to support different Vividict
subclasses at each level in the hierarchy: i.e. Company
, Department
, and Employee
. Each subclass defines a class atribute named subtype
the the Vividict
base class' __missing__()
will use when creating missing key values. I also added __repr__()
method to each one to make instance print out all the items they contain.
This is just a proof-of-concept and I really don't know if you can use it or not, but it should give you a good idea of one way of doing what you want with some fairly readable syntax.
class Vividict(dict): # Base class.
subtype = dict
def __missing__(self, key):
value = self[key] = self.subtype(key)
return value
class Employee: # Leaf - Regular class
def __init__(self, given_name):
self.given_name = given_name
def __repr__(self):
return f'{self.__class__.__name__}({self.given_name!r})'
class Department(Vividict): # Branch.
subtype = Employee
def __init__(self, dept_name):
self.dept_name = dept_name
def __repr__(self):
return (f'{self.__class__.__name__}({self.dept_name!r})' + '\n '
+ repr(list(self.values())))
class Company(Vividict): # Root of tree.
subtype = Department
def __init__(self, co_name):
self.co_name = co_name
def __repr__(self):
return (f'{self.__class__.__name__}({self.co_name!r})' + '\n '
+ repr(list(self.values())))
company = Company('MS')
company['Finance']['George'].full_name = 'George Brown'
company['Finance']['Mary'].full_name = 'Mary Jones'
print(company)
Output:
Company('MS')
[Department('Finance')
[Employee('George'), Employee('Mary')]]