Python 3中继承外部父级嵌套类的嵌套类

3
假设我有以下Python 3中的类:
class CoolCar:
    @classmethod
    def myWheels(cls):
        cls.Wheels().out()
    class Wheels:
        def __init__(self):
            self.s = "I'm round!"
        def out(self):
            print(self.s)

一切顺利。现在我想要一个派生类:

class TerribleTank(CoolCar):
    class Wheels(CoolCar.Wheels):
        def __init__(self):
            self.s = "I'm square!!"

这个工作的效果符合我的期望:

CoolCar.myWheels()
TerribleTank.myWheels()

但是让我感到困扰的是,在定义 TerribleTank 时,我必须两次写入 CoolCar。因此,我尝试了以下方法:

class TerribleTank(CoolCar):
    class Wheels(super().Wheels):
        def __init__(self):
            self.s = "I'm square!!"

以下代码无法正常工作。现在,我知道它无法正常工作是因为super()正在寻找第一个参数self/cls来开始搜索。

所以最后我的问题是:是否有类似的方法可以正常工作,这样我就不需要显式地编写第二个CoolCar


2
你为什么要把类放在类里面? - Padraic Cunningham
@PadraicCunningham:这只是一个大大简化的例子,实际情况要复杂得多。我使用子类的原因有很多(其中一个是命名空间问题),但也因为它允许我在我的某个类中编写Wheels.foo,并且只要有正确版本的Wheels,它就可以正常工作。更多信息,请参阅Marc Summfield的Python in Practice中的工厂模式章节。 - Steve D
@JohnMee: TerribleTank将覆盖此Wheel类。现在,任何继承自TerribleTank的类都会怎么样?将原始的Wheels类放在模块级别只会将问题提升一代,而不是解决它。 - Steve D
至少我不知道如何按你想要的方式使用super,Wheels对CoolCar一无所知。 - Padraic Cunningham
你是否意识到,在那个按照你的期望运行的例子中,你实际上没有实例化一个酷车或可怕坦克,而是有效地运行了一个静态方法? - John Mee
显示剩余3条评论
1个回答

2

怎么样:

class CoolCar:
    @classmethod
    def myWheels(cls):
        cls.Wheels().out()
    class Wheels:
        def __init__(self):
            self.s = "I'm round!"
        def out(self):
            print(self.s)

class TerribleTank(CoolCar):
    class Wheels(TerribleTank.Wheels):
        def __init__(self):
            self.s = "I'm square!!"

>>> TerribleTank.myWheels()
I'm square!!

基本上,当你在TerribleTank中继承CoolCar时,你将TerribleTank.Wheels设置为对CoolCar.Wheels的引用,直到你在TerribleTank定义内部使用自己新的定义来屏蔽它。因此,我相信这符合您的期望,即在TerribleBank定义中不重复使用 CoolCar
希望能对您有所帮助!

请注意:如果您因为两次使用“TerribleBank”而仍然不满意,可以尝试使用元类,但就个人而言,我宁愿睡觉也不愿意过度设计如此简单的东西 ;) - zmo
1
将其调整为直接调用TerribleTank.myWheels(),他不想创建坦克或汽车;只需要它们的轮子。 - John Mee
这在技术上是正确的(最好的正确方式),但我仍然希望有一种更简洁的方法来完成这个任务。 - Steve D
好的,更加清晰的方法是你所建议的,但可能不适合你,这是第二选择,然后你可以使用一些元类混乱。但有句话说得好:当你遇到需要元类来解决的问题时,最终会遇到一个元问题;-) - zmo

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接