簡體   English   中英

動態添加類繼承

[英]Adding class inheritance dynamically

我想用python創建動態類繼承。 例如( x可能是一個隨機數)

#!/usr/bin/env python
# -*- coding: utf-8 -*-

class Test3(object):
  def sub(self):
    self.c = self.a - self.b

class Test2(object):
  def add(self):
    self.c = self.a + self.b


class Test1(object):
  def __init__(self):
    self.a = 1
    self.b = 2
    self.c = 0


if x >= 0:
  test = Test1
  ## do something to load Test2 methods
  test.add()
  print (test.c)
elif x >= 10:
  test = Test1
  ## do something to load Test3 methods
  test.sub()
  print (test.c)
else:
  test = Test1
  ## do something to load Test3 & Test2 methods
  test.add()
  print (test.c)
  test.sub()
  print (test.c)

我嘗試了不同的方法來使其正常工作。 除了靜態實現子類外,我無法管理,這不是我想要的:

class Test1(Test2, Test3)

我也不想在變量中加載對象並獲得有關變量名稱的訪問權,例如:

test1.test3.sub()

您可以通過幾種技巧來實現這種目的。

首先,您可以像這樣做一些丑陋的事情:

def extend(instance, new_class):
    """Add new_class mixin to existing instance"""
    instance.__class__ = type(
            '%s_extended_with_%s' % (instance.__class__.__name__, new_class.__name__), 
            (instance.__class__, new_class), 
            {}
        )

你可以這樣使用

   extend(test , Test2 )

但是我通常更喜歡在初始化之前創建動態類型,而不是覆蓋__class__,因此您可以在第一個示例中使用上面的方法而不是上面的方法

   custom_class = type('special_extended_class', ( Test, Test2 ), {} )
   test  = custom_class()

請注意,在上面的Test和Test2是變量引用,因此您可以在此處使用任何內容,但是與以下更易讀的操作沒有太大不同。

  class1 = Test
  class2 = Test2
  class TmpClass(class1, class2):pass
  test = TmpClass()

我不太了解您為什么要那樣做。 我將創建一個基礎測試類,然后基於該類繼承不同的方法。

class BaseTest(object):
    def __init__(self):
        super().__init__()

        self.a = 1
        self.b = 2
        self.c = 0

class Test3(BaseTest):
    def sub(self):
        self.c = self.a - self.b

class Test2(BaseTest):
    def add(self):
        self.c = self.a + self.b

class Test4(Test3, Test2):
    pass

if __name__ == '__main__':
    x = -1
    if x >= 10:
        test = Test3()
        ### load test3 methodes
        test.sub()
        print (test.c)

    elif x >= 0:
        test = Test2()
        ## load test2 methodes
        test.add()
        print (test.c)

    else:
        test = Test4()
        ### load test 2 & test 3 methodes
        test.add()
        print (test.c)
        test.sub()
        print (test.c)

如果您真的想要動態的東西,那么必須在導入時設置x值

import random

class Test3(object):
    def sub(self):
        self.c = self.a - self.b

class Test2(object):
    def add(self):
        self.c = self.a + self.b

class Test4(Test3, Test2):
    pass

val = random.randint(0, 3)
print(val)
x = {0: object,
     1: Test3,
     2: Test2,
     3: Test4,
     }.get(val, object)
print(x)

class BaseTest(x):
    def __init__(self):
        super().__init__()

        self.a = 1
        self.b = 2
        self.c = 0


if __name__ == '__main__':
    b = BaseTest()
    print(b.c)

您可能可以按照rgammans的建議通過手動設置類成員字典的成員來完成這項工作,但是最簡單的方法是使用exec:

super = 'list'
exec('class Awesome(' + super +'):\n  pass')

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM