Warning: file_get_contents(/data/phpspider/zhask/data//catemap/8/python-3.x/18.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Python Django,与抽象实体的多对一关系_Python_Python 3.x_Django_Django Models_Django Rest Framework - Fatal编程技术网

Python Django,与抽象实体的多对一关系

Python Django,与抽象实体的多对一关系,python,python-3.x,django,django-models,django-rest-framework,Python,Python 3.x,Django,Django Models,Django Rest Framework,假设对象在一个数组中包含多种类型的对象(模型),如页面,可以包含帖子、博客、图片,数量或顺序任意,用户可以向下滚动并看到以下元素,这取决于页面,下一个元素是这些类型的元素之一。因此,页面可以包含: APost APost A图片 或者一些完全不同的东西,比如: A图片 一个博客 A图片 元素可以是一个抽象实体,其属性为外键,将自身与页面关联,其继承将获得对该关系的访问权: class Page(models.Model): ... class PageElement(model

假设对象在一个数组中包含多种类型的对象(
模型
),如
页面
,可以包含
帖子
博客
图片
,数量或顺序任意,用户可以向下滚动并看到以下元素,这取决于
页面
,下一个元素是这些类型的元素之一。因此,
页面
可以包含:

  • A
    Post
  • A
    Post
  • A
    图片
  • 或者一些完全不同的东西,比如:

  • A
    图片
  • 一个
    博客
  • A
    图片
  • 元素可以是一个抽象实体,其属性为
    外键
    ,将自身与
    页面
    关联,其继承将获得对该关系的访问权:

    class Page(models.Model):
        ...
        
    class PageElement(models.Model):
        page = models.ForeignKey(Page, verbose_name="Page", on_delete=CASCADE)
    
        class Meta:
            abstract = True
    
    class Post(PageElement):
        ...
    
    class Blog(PageElement):
        ...
    
    class Picture(PageElement):
        ...
    
    使用这种方法,您可以使用REST序列化程序序列化
    页面
    ,但您无法访问
    页面元素集
    ,而是需要调用
    post\u集
    blog\u集
    图片集
    ,并取消对象的顺序

    只需在
    外键
    中添加一个
    相关的\u名称
    键,我们就会得到一个错误:

    pages.Picture.page: (fields.E305) Reverse query name for 'Picture.page' clashes with reverse query name for 'Post.page'.
            HINT: Add or change a related_name argument to the definition for 'Picture.page' or 'Post.page'.
    
    问题是:您如何在Django实现这种关系?


    这样,您就可以拥有一组
    PageElement
    实例的订单集,并能够拥有所需的订单。

    因为您希望按顺序查询多个模型,并且可以看到您的模型处于
    模型是一个PageElement
    关系中,然后,与从抽象模型继承不同,您需要一个带有公共模型的
    OneToOneField

    class PageElement(models.Model):
        POST = 'PO'
        BLOG = 'BL'
        PICTURE = 'PI'
        ELEMENT_TYPE_CHOICES = [
            (POST, 'Post'),
            (BLOG, 'Blog'),
            (PICTURE, 'Picture'),
        ]
        element_type = models.CharField(
            max_length=2,
            choices=ELEMENT_TYPE_CHOICES,
            default=POST,
        )
        # common fields
    
    class Post():
        page_element = models.OneToOneField(
            PageElement,
            on_delete=models.CASCADE,
            related_name = "post"
        )
    
    class Blog():
        page_element = models.OneToOneField(
            PageElement,
            on_delete=models.CASCADE,
            related_name = "blog"
        )
    
    class Picture():
        page_element = models.OneToOneField(
            PageElement,
            on_delete=models.CASCADE,
            related_name = "picture"
        )
    

    如果需要,您可以从具有
    OneToOneField
    的公共抽象类继承,以方便使用。

    太好了!,这确实解决了问题,谢谢!