【问题标题】:Python : How is sub class variable accessible by superclass functions when called by an object of sub-classPython:当被子类的对象调用时,超类函数如何访问子类变量
【发布时间】:2020-05-10 16:13:55
【问题描述】:
initialTreeCom=['ADD_CHILD None King_Shan Male','ADD_CHILD None Queen_Anga Female',
                 'AM King_Shan Queen_Anga','ADD_CHILD Queen_Anga Chit Male']

famTree=familyTree.FamiltyTree(initialTreeCom)
result=famTree.excommand('GET_RELATIONSHIP Chit Father')
print(result)

第一季度。当我创建一个类 FamilyTree 的对象时,它继承自类 RelationshipsFamilyTree 类的 excommand 函数如何调用父类的函数

getattr(self, argument[2].replace('-','_'))(argument[1])

但是当我使用super(因为我想访问父类的函数)而不是self获取gettr函数的函数引用时抛出错误?

第二季度。超类Relationships的被调用函数Father如何使用self.familyMembers访问子类FamilyTree的变量familyMembers

    class Person():
            def __init__(self,mother,name,gender):
                self.name=name
            self.gender=gender
            self.mother=mother
            self.marriedTo=None

        def add_partner(self,marriedTo):
            """
            Assigns passed marriedTo value to marriedTo attribute to calling objects
            """
            if marriedTo != self.marriedTo:
                self.marriedTo=marriedTo

    class FamiltyTree(Relationships):
        familyMembers=OrderedDict()
        def __init__(self,initialTree):        
            for i,line in enumerate(initialTree):
                # print('executing command',i,' : ',line)
                self.excommand(line)

        def excommand(self,command):
            """
            Executes the passed command
            Commands : ADD_CHILD, GET_RELATIONSHIP
            """
            argument=command.split()
            if argument[0]=='ADD_CHILD':
                # print('adding child')
                p=Person(argument[1], argument[2], argument[3])
                return self.add_Person(p)
            if argument[0]=='AM':
                # print('adding married to')
                return self.add_MarriedTo(argument[1], argument[2])
            if argument[0]=='GET_RELATIONSHIP':
                if argument[1] not in self.familyMembers:
                    return 'PERSON_NOT_FOUND'
                # print('getting relationship',argument[2], 'for : ',argument[1])
                **res= getattr(self,argument[2].replace('-','_'))(argument[1])**
                if res:
                    return ' '.join(res)
                return None

        def add_Person(self,person):
            """
            Adds passed Person to Family members, of calling object of FamiltyTree
            """
            if person.mother!='None' and  person.mother not in self.familyMembers:
                return 'PERSON_NOT_FOUND'
            if isinstance(person,Person) and person.name not in self.familyMembers and (person.mother=='None' or self.familyMembers[person.mother].gender=='Female'):
                self.familyMembers[person.name]=person
                return 'CHILD_ADDITION_SUCCEEDED'
            else:
                return 'CHILD_ADDITION_FAILED'

        def add_MarriedTo(self,person1,person2):
            """
            sets marriedTo Relationship among both passed person objects to each other.
            """
            if person1 in self.familyMembers and person2 in self.familyMembers:
                for key , value in self.familyMembers.items():
                    if key==person1:
                        value.add_partner(person2)
                    if key==person2:
                        value.add_partner(person1)
                return True
            else:
                return False

    class Relationships():

        def Father(self,name):
            """
            Finds Father of passed person name
            """
            if name in self.familyMembers:
                for key , value in self.familyMembers.items():
                    if self.familyMembers[self.familyMembers[name].mother].marriedTo==key:
                        return key
            return None

【问题讨论】:

    标签: python inheritance parent-child subclass superclass


    【解决方案1】:

    A1。 getattr() 正在搜索名称与您传递给它的字符串相对应的成员。在您的情况下,名称是 Father。这是一种将字符串映射到用户输入(在您的情况下为argument[2])的便捷方式,以便您可以查看Relationships 类中是否存在该关系的实现。

    这很聪明。现在您只需将其他关系的实现添加到Relationship 类,而无需修改GET_RELATIONSHIP 的实现。

    或者,您可以将Father 实现为:

    if argument[2] == 'Father':
       res = self.Father(argument[1])
    

    但是你必须为你想要实现的每种类型的关系都这样做(例如,BrotherCousin)。

    这个Relationships 类使您可以轻松地通过遍历家谱来实现个人关系。 Father() 实现就是一个很好的例子。

    A2。因为当 Python 遇到self.x 时,它首先在当前类中搜索数据属性x,如果没有找到,则继续搜索类属性x,并将其用于@987654336 的后续操作@。在您的情况下,familyMembers 是类属性,它恰好位于超类Relationships 中。 super 只查看数据成员。

    关于类和实例属性的精彩讨论here

    【讨论】:

    • 是的,出于同样的原因,我添加了 getattr()。我的问题是为什么我能够使用 'self' 访问父类的函数,而我的第一直觉是使用 'super' ,但令我惊讶的是它抛出了错误。在第二季度,我基本上对超类函数如何使用 'self' 访问子类的类成员感到困惑。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2012-04-09
    • 1970-01-01
    • 2017-09-13
    • 2021-05-05
    • 1970-01-01
    • 1970-01-01
    • 2016-03-08
    相关资源
    最近更新 更多