ListProperty的密钥与App Engine中的多对多

时间:2009-09-04 01:33:53

标签: google-app-engine models

作为一个假设的例子,我有一个模型TodoItem和一个模型TodoList。 TodoList具有TodoItems的有序列表,并且任何一个TodoItem可以属于任意数量的TodoLists(多对多)。除了TodoList中TodoItem的顺序之外,不需要存储关于其关系的其他信息。在数据存储中表示这个的最佳方法是什么?

有两种实现方法 - 给TodoList类一个db.Key的ListProperty,它将引用TodoItem:

class TodoList(db.Model):
  items = db.ListProperty(db.Key)

或创建一个也包含订购信息的ListItem模型:

class TodoListItem(db.Model):
  item = db.ReferenceProperty(TodoItem)
  list = db.ReferenceProperty(TodoList)
  order = db.IntegerProperty()

我肯定会通过对模型进行非规范化来优化它,但是预优化,任何一种表示都有优势吗?

3 个答案:

答案 0 :(得分:10)

这取决于几个因素:

  • 除了订单之外,您是否需要存储关系本身的信息?例如,许多订单和产品之间的许多需要存储每种产品的数量。
  • 您是否需要将关系方面的一千多个项目与“较小”基数相关联(例如,> 1000个待办事项,或> 1000个项目列表)?
  • 您是否通常想要一次检索所有相关项目,或者您想要更具选择性?

如果您需要额外的信息,或者您的关联中包含许多元素,或者只需要检索其中的一些元素,则关系实体可能是更好的选择。在其他情况下,列表可以更容易和更快。在todo列表的情况下,我会说一个键列表绝对是最好的方式。

答案 1 :(得分:1)

除了在关系上下文中,人们正在推动规范化(当然,在关系情况下非常可取!)单独的TodoListItem“关系类”对我来说似乎有些过分,而且在某种程度上“笨拙”关于问题的原因与人们编码的方式有关。然而,优化方面肯定会更容易找到项目所在的所有列表。

答案 2 :(得分:0)

鉴于TodoListItem可以属于多个TodoLists,我担心有一个单一的属性可以适用于该项所属的每个列表。我认为该项目对于它所属的每个列表都需要一个订单。