Django:从一个超类继承,访问多个子类的某个属性



我的目标是访问子类的属性,而不事先知道选择了两个子类中的哪一个子类(多选类(

理想情况下,SuperClass中有一个属性会根据选择的SubClass而变化。

原因是我直接从子类创建了窗体,并使用SuperClass作为访问值的入口点。

我知道我可以在hasattr(horse(中使用true或false,但理想情况下,我会问是否有一个更整洁的解决方案,比如SubClass可以向SuperClass发出使用了哪个SubClass的信号。

例如,对于我的列表中的产品8

subclass = getattr(Product(8), 'subclass', 0)
print(subclass)
>> Horse

place = Product.location
Print(place)
>> Stable

整个"问题"源于我通过SubClass Forms创建产品的事实,同时后面的大部分逻辑都是自上而下的,从产品开始

class Product(models.Model):
product_name = models.Charfield(max_length=20)
class Car(Product):
engine = models.Charfield(max_length=20)
location = models.Charfield(default="Garage", max_length=20, editable=False)
product = models.OneToOneField(Product, parent_link=True, on_delete=models.CASCADE)
class Horse(Product):
saddle_model = models.Charfield(max_length=20)
location = models.Charfield(default="Stable", max_length=20, editable=False)
product = models.OneToOneField(Product, parent_link=True, on_delete=models.CASCADE)

如果您想从Product模型访问其他模型属性,您可以在Product上实现一个属性方法,该方法检查Product及其相关模型之间的反向关系,然后返回适当的位置(https://docs.djangoproject.com/en/2.1/topics/db/examples/one_to_one/)。

class Product(models.Model):
product_name = models.CharField(max_length=20)
@property
def location(self):
"""Return the location of the related subclass"""
if self.car:
return self.car.location
elif self.horse:
return self.horse.location
else:
return None
@property
def product_subclass(self):
"""Return the location of the related subclass"""
if self.car:
return self.car
elif self.horse:
return self.horse
else:
return None

这应该允许你这样使用它:

car_product = Product.objects.create(product_name="Car Product")
car = Car.objects.create(engine="engine", location="123 Fake Street", product=car_product)
print(car_product.location)  # Prints "123 Fake Street"
horse_product = Product.objects.create(product_name="Horse Product")
horse = Horse.objects.create(saddle_model="Buckingham", location="1982 Old Street", product=horse_product)
print(horse_product.location)  # Prints "1982 Old Street"

如果你想做一些类似的事情来返回子类:

print(car_product.product_subclass)  # Prints <Car object>
print(horse_product.product_subclass)  # Prints <Horse object>

这些属性方法需要数据库查询来检查Car和Horse表,因为关系存储在这些表上作为product_id列。因此,为了确定product.car是否有效,ORM执行类似于Car.objects.get(product_id=product.pk)的查询

最新更新