Python 用Django编写合适的数据模型

Python 用Django编写合适的数据模型,python,django,python-3.5,Python,Django,Python 3.5,我正试图写一个Django模型,但当我在文档中读得越来越深入时,我发现我必须考虑太多的事情,我真的对我必须记住的所有考虑事项感到困惑 我最基本的疑问是“当我定义两个类时,我在其中包括对另一个类的引用时…” a) 类a只有一个类B实例 b) A类必须有一个 只有一个B类实例 c) 类A有许多类B实例 d) A类是B类的一种(正如餐厅是 (商业) “…以及在创建这些对象时如何创建/管理这两个类” 我希望有人能更容易地解释。我想,有了这四件事,我也许可以自己写模型了 Django文档仍然是一个很好

我正试图写一个Django模型,但当我在文档中读得越来越深入时,我发现我必须考虑太多的事情,我真的对我必须记住的所有考虑事项感到困惑

我最基本的疑问是“当我定义两个类时,我在其中包括对另一个类的引用时…”

  • a) 类a只有一个类B实例
  • b) A类必须有一个 只有一个B类实例
  • c) 类A有许多类B实例
  • d) A类是B类的一种(正如餐厅是 (商业)
“…以及在创建这些对象时如何创建/管理这两个类”

我希望有人能更容易地解释。我想,有了这四件事,我也许可以自己写模型了

Django文档仍然是一个很好的起点,对于初学者和专业人士来说都非常全面。除了阅读文档和玩示例,没有其他捷径可以掌握它

案例a)a类只有一个B类实例
UserModel
代表
A
UserProfile
代表
B

假设我们有一个
UserModel
,并且需要另外一个表来保存额外的信息,比如说
UserProfile
。我们允许
UserProfile
为空。然后我们可以使用
OneToOneField
绑定这两个类

模型定义 如何从B访问A,反之亦然 案例b)A类必须有一个且只有一个b类实例
UserModel
代表
A
UserProfile
代表
B

对于模型定义,它几乎与案例a)相同。但是我们需要确保B与A共存,因此我们需要删除
Blank
null
。我们必须使用
post\u save
hook使suer B也被创建为带有A的保存

模型定义 如何从B访问A,反之亦然 与案例a相同)

案例c)A类有许多B类实例
Author
代表
A
Book
代表
B

例如,
Author
是一个保存图书作者信息的模型,一个作者可能写零本或多本书,我们将其命名为
book
作为模型。(假设每本书只允许一位作者)

如何从B访问A,反之亦然 如果你允许一本书有许多作者,那么我们应该使用
ManyToManyField
而不是
ForeignKey
手册
模型定义更改为:

class BookAuthor(models.Model):
    author = model.ForeignKey(Author)
    book = model.ForeignKey(Book)
    publish_at = model.DateTimeField(auto_add=True)

class Book(models.Model):
    book_name = models.CharField('name of the book', max_length=50)
    # through is used to tell django, we have defined another relationship table to bind Author and Book model.
    authors = models.ManyToManyField(Author, through='BookAuthor')
如何从B访问A,反之亦然 案例d)A类是B类的一种类型(餐厅也是一种商业类型)
Place
代表
B
Library
Restaurant
代表
A

例如,我们定义了一个泛型类
Place
,而
Library
可以是一个场所,与
餐厅
相同

模型定义 如何使用A和B 对于上述情况,django将在db中创建一个
Place
表,因为它也是一个模型,如果您不知道要创建什么,并将其视为
Abstract
类作为其他编程语言,您可以按如下方式重新定义它:

class Place(models.Model):
   address = models.CharField('address', max_length=100)

   class Meta:
       abstract = True

我在Django方面没有任何经验,但建议您仔细阅读有关数据建模的文档,您可能会了解它的实际工作原理。。。。问题是什么?该代码如何不符合您的规范?你在哪里卡住了?请澄清。@Bakuriu问题很简单,“我如何才能编写一个符合所有这些要求的模型”,我陷入了这样的困境,它太复杂了,我真的不知道从哪里开始。我写的代码并不能完成我需要的所有事情。如果你读了这两本书,你会发现它漏掉了。@Bakuriu我写下了我的问题来澄清它。希望现在它能帮助更多。对于a)使用
OneToOneField
,同时将
blank
null
设置为True,对于b)使用
OneToOneField
,对于c)使用
ForeignKey
,对于d)使用
模型继承
。但我认为你不能同时满足这四个要求。非常感谢。这帮了大忙。
from django.db import models
from django.dispatch import receiver
from django.db.models.signals import post_save, pre_save

class UserModel(models.Model):
    name = models.CharField('username', max_length=20)

class UserProfile(models.Model):
    nickname = models.CharField('nick name', max_length=50)
    user = models.OneToOneField(UserModel,on_delete=models.CASCADE)

@receiver(post_save, sender=UserModel)
def create_auth_token(sender, instance=None, created=False, **kwargs):
    # This hook is automatically called when the UserModel is created, this is used to make suer UserProfile is also created when UserModel is created.
    if created:
        UserProfile.objects.create(user=instance)
class Author(models.Model):
    name = models.CharField('name of the author', max_length=20)

class Book(models.Model):
    book_name = models.CharField('name of the book', max_length=50)
    author = models.ForeignKey(Author, related_name='books')
# access B from A
author = Author.objects.get(pk=1)
books = author.books
# first book
book_name = books[0].book_name

# access A from B
book = Book.objects.get(pk=1)
author_name = book.author.name
class BookAuthor(models.Model):
    author = model.ForeignKey(Author)
    book = model.ForeignKey(Book)
    publish_at = model.DateTimeField(auto_add=True)

class Book(models.Model):
    book_name = models.CharField('name of the book', max_length=50)
    # through is used to tell django, we have defined another relationship table to bind Author and Book model.
    authors = models.ManyToManyField(Author, through='BookAuthor')
author = Author.objects.get(pk=1)
first_book_name = author.book_set.order_by('publish_at')[0].book_name

book = Book.objects.get(pk=1)
author_names = [author.name for author in book.author_set.all()]
class Place(models.Model):
   address = models.CharField('address', max_length=100)

class Library(Place):
   num_of_books = models.IntegerField('NO. of books in the library')

class Restaurant(Place):
   restaurant_type = models.CharField('The type of the restaurant', max_length=10)
lib = Library.objects.get(pk=1)
lib.address  # get the library address
lib.num_of_books  # get the no. of books in this library 

rest = Restaurant.objects.get(pk=1)
rest.address  # get the restaurant address
rest.restaurant_type  # get the restaurant type
class Place(models.Model):
   address = models.CharField('address', max_length=100)

   class Meta:
       abstract = True