0

我对应用程序引擎数据存储相当陌生,但知道它的设计更像是一个 Hashtable 而不是数据库表。这使我认为“一般”具有更少的行(实体)和更多的列(对象属性)会更好。

也就是说,您可以创建一个Car具有属性的对象,color或者count您可以使用属性redCountblueCount、来创建它greenCount,假设您知道所有颜色(尺寸)。如果您要存储这些对象的实例,您将拥有三个或一个:

对于每种颜色和计数,保存新实体: "red", 3 "blue", 8 "green", 4

或者为每种可能的颜色保存一个具有属性的实体:3, 8, 4

显然,后一种方法存在一些设计挑战,但想知道摆脱关系思维的建议是什么?似乎数据存储区对数百个“列”/属性非常满意。

4

3 回答 3

1

试图摆脱关系思维的好工作。摆脱行/表思维是件好事。

至少在编程方面,更接近的近似值是将实体视为远程存储的数据结构或类实例。这些实体具有属性。与实体分开的是索引,它本质上存储与某些属性标准匹配的实体列表。

当您编写实体时,数据存储会更新内存/存储中的该实例,然后更新所有索引。

当您进行查询时,您实际上是遍历其中一个索引列表。

这应该为您提供一个考虑数据存储的基本框架。

当您为数据存储进行设计时,您通常必须针对成本进行设计,在较小程度上还需要考虑性能。在写入方面,您希望最小化索引的数量。在读取方面,您希望最大限度地减少正在读取的实体数量,因此为红色、蓝色、绿色设置单独实体的想法可能不是一个好主意,如果您经常需要回读数字,则读取成本会增加三倍红色/蓝色/绿色汽车。可能有一些非常模糊的角落案例,这是有道理的。

您的设计考虑通常应遵循以下原则:

  1. 我需要做哪些类型的查询?
  2. 我如何构建我的数据以使这些查询易于执行(因为 GAE 查询功能有限)?如果我以某种方式复制数据,查询会更容易吗?我是否能够自己维护这些复制的数据?
  3. 如何在更新实体时尽量减少需要更新的索引数量?
  4. 是否存在我必须具有完全一致性并因此需要调整结构以便进行一致查询的特殊情况?
  5. 有没有我需要注意的写入性能案例。

在不确切知道您将要进行哪种查询的情况下,这个答案可能不正确,但它应该说明您可能想如何思考这个问题。

我假设你有一个人们注册他们的汽车的应用程序,并且你有一些仪表板可以轮询数据存储并显示每种颜色的汽车数量,具有颜色的 Car 类的传统机制,计数属性仍然有意义,因为它最大限度地减少了索引属性的数量,从而降低了您的写入成本。

这是一个有点奇怪的例子,因为我不知道您是否只想拥有一个跟踪您的计数的实体(在这种情况下,您甚至不需要进行查询,您只需获取该计数),或者如果您有许多可以获取和汇总的计数实体。

如果用户更新修改了相同的实体,您可能会遇到性能问题,您应该阅读以下内容:https ://developers.google.com/appengine/articles/sharding_counters

于 2013-09-27T16:34:59.650 回答
0

我认为可以肯定地说,在数据库模型中为每个实体(行)拥有大量属性(列)并没有显着的性能损失。很多行(实体)甚至很多表(数据库类)也不会受到惩罚。如果我在做你的例子,我肯定会为颜色和计数设置单独的属性。我们总是明确地调用 indexed=False/True 以确保我们避免在只有几个属性被索引时(忘记默认值为 True)时想知道为什么索引如此之大的可怕问题。尽管 GAE 为您提供了很好的属性,例如可以索引的列表,但这些特殊属性并非没有开销。每当您使用它们时,请充分了解它们。

我认为在绘制设计时要记住 GAE 很重要的一件事是,标准查询速度很慢,而且速度很慢意味着延迟增加,延迟增加会导致更多实例和更多费用(以及其他挫折)。在默认使用标准查询之前,请始终询问(这是否是代码的关键任务部分)您是否可以通过设置更非规范化的数据结构来完成相同的任务。例如,使用公共键将一组实体链接在一起,然后执行一系列 get_by_id() 调用通常是有利的(这样做时一定要管理 ndb 的自动内存缓存 - 并非所有内容都需要缓存)。祖先查询也比标准查询快得多(但对家庭组施加了每秒更新 1 次的限制。)

结论:在合理范围内,实体(行)中的数字属性(列)以及类(表)的总数不会强加任何实际问题。但是,如果您来自标准关系数据库背景,您的倾向将是使用类似 SQL 的查询来移动您的逻辑。请记住,在 GAE 中,标准 GQL 查询速度慢且成本高,并且总是考虑使用非规范化链接来避免它们。GAE 是一个大型、扁平、高性能的类 noSQL 资源。就这样使用它。花额外的时间来避免依赖 GQL 查询,这将是值得的。

于 2013-09-27T14:47:58.900 回答
0

我建议不要在一个单元格中以您自己的标准存储东西。除非它是用 JSON 或类似的东西编码的。

{'red':3, 'blue':4}

JSON 是可以的,因为它可以很容易地解码为 java 中的数据结构,如列表或其他东西。

应用程序中的许多列没有任何问题。通过设置红色、蓝色和绿色列,您将获得更多收益。必须有大量的列才能看到大幅减速。

于 2013-09-27T05:55:07.057 回答