【问题标题】:Google NDB: Best way to read child entities from an entity, repeated property vs regular query?Google NDB:从实体中读取子实体的最佳方法,重复属性与常规查询?
【发布时间】:2014-09-02 22:44:53
【问题描述】:

假设我有这个非常简单的父/子关系(任何Answer 类实例总是有一个Question 父级)

class Answer(ndb.Model):
    content = ndb.StringProperty()
    timestamp = ndb.DateTimeProperty()

    def to_message():
        """Returns a protoRPC message object of the answer"""


class Question(ndb.Model):
    content = ndb.StringProperty()
    answers = ndb.KeyProperty(repeated = True, kind = 'Answer')

    def to_message(self):
        """Returns a protoRPC message object of the question"""

这两个to message 方法只是用来返回一个protoRPC 对象。 问题是:在我的to_message 方法中,在Question 类中,如果我想获取所有子Answer 实例,检索它们,并使用它们自己的to_message 方法将它们变成一个漂亮的rpc 消息,是不是更好:

  • 遍历 anwers 重复的 KeyProperty 列表
  • 对“父”属性使用过滤器进行查询,并遍历它输出的列表

就 NDB 访问而言,第一种方法似乎是最好的,但由于无论如何我们都会超过免费限制,我更想知道数据存储区在获取内容方面是否比我更有效,遍历该列表。

编辑:最初的问题实际上有一个非常简单明了的答案:第一种方式。 真正的问题是,如果我必须根据属性过滤掉一些Answer 实体(例如timestamp):是使用过滤器查询更好,还是遍历列表并使用条件来收集只有“有趣”的实体?

【问题讨论】:

    标签: google-app-engine google-cloud-datastore app-engine-ndb


    【解决方案1】:

    使用该架构,您无需查询任何内容,因为您已经将每个答案的键作为question_entity.answers 中的键列表获得

    因此,您只需使用这些键获取答案。如果您在一次操作中获得所有答案,那就更好了。

    list_of_answers = ndb.get_multi(question_entity.answers)
    

    (更多信息NDB Entities and Keys

    另一方面,如果你用Answer 中的KeyProperty 建模这种关系:

    class Answer(ndb.Model):
        question = ndb.KeyProperty(Question)
        content = ndb.StringProperty()
        timestamp = ndb.DateTimeProperty()
    
    def to_message():
        """Returns a protoRPC message object of the answer"""
    

    或与祖先:

    answer = Answer(parent=question_entity.key)
    

    在这些情况下,您应该使用普通查询来检索答案:

    answers = Answer.query(Answer.question == question_entity.key)
    

    或祖先查询:

    answers = Answer.query(ancestor = question_entity.key)
    

    分别。

    这意味着两个工作:查询索引加上获取数据存储。总之,在这种情况下,第一种方法检索数据存储数据的成本更低。

    【讨论】:

    • 感谢您的回答...我认为我目前的问题有点愚蠢。真正的问题是:假设我有一个键列表,并且我想获得一个实体列表,这些实体被某个属性(例如时间戳值)的某些条件过滤掉。查询还是遍历列表更有效?
    • 在这种情况下,使用您的架构,查询是不可行的。您应该遍历所有实体,并使用 python 代码进行过滤。另一个选项是使用KeyProperty(Question)Answer,就像上面的例子一样。在这种情况下,您可以按问题过滤答案,也可以按同一查询中的其他属性过滤答案。最后一个选项更便宜(更快),因为您只检索您需要的答案。
    • 第三个(如果算上祖先的话,是第四个)选项使用Structured Property。就像它有优点和缺点一样。
    • 为什么不能查询?如果它为任何 Answer 实体设置了我的父属性,我应该能够查询,不是吗? (使用“祖先”过滤器)
    • 我就是这么说的。如果您设置了父母,您可以进行祖先查询。如果不设置父级,则必须遍历实体列表。
    【解决方案2】:

    使用键列表上的ndb.get_multi 来获取答案,然后迭代调用它们的 to_message 方法将是最有效的。

    【讨论】:

    • oyu 能否更具体地说明您的方法的效率?
    猜你喜欢
    • 2012-07-15
    • 1970-01-01
    • 2011-12-06
    • 2015-05-10
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多