数据库包含与另一个表具有一对多关系的表。第一个表有很多列,第二个表只有几个 - 例如在这个数据库设计中:
┌───────────────────┐
│item │
├───────────────────┤
│id: BIGINT │←┐
│name: VARCHAR(100) │ │
│ ... │ │
│<many attributes> │ │
│ ... │ │
└───────────────────┘ │
│
┌───────────────────┐ │
│item_tag │ │
├───────────────────┤ │
│item_id: BIGINT │─┘
│name: VARCHAR(100) │
│color: VARCHAR(50) │
└───────────────────┘
检索所有项行的最佳做法是什么,以及它们的标记名称和标记颜色 - 例如将它们显示在带有标签的项目列表中。
可能的解决方案1
在项目ID上加入两个表格:
SELECT * FROM item JOIN item_tag ON id = item_id;
表 item 有很多列包含大量数据的问题,因为 item 中的每一行都会在查询结果中多次出现。许多数据必须通过网络传输到客户端。此外,客户端必须将所有行与相同的项目数据合并,以获得每个项目的相应标记。
可能的解决方案2
首先查询项目......
SELECT * FROM item;
...然后检索每个项目的标签:
SELECT * FROM item_tag WHERE item_id = ?;
但这需要多个单独的SQL查询 - 每个项行一个 - 这可能很慢;也是由于每个查询请求的网络延迟。
可能的解决方案3
一次查询两个表......
SELECT * FROM item;
SELECT * FROM item_tag;
...标签到项目的映射由客户完成。
此处查询的数量和传输的数据量是最低的,但客户端的额外处理工作是必需的。如果仅查询 item 的子集,则可以修改选择 item_tag 的查询以仅返回查询项的标记。
还有其他/更好的解决方案吗?最好的方法是什么?
我更喜欢使用Amazon Redshift的有限数据库功能的解决方案,它没有那么多奇特的功能,比如数组类型。
答案 0 :(得分:0)
如果您已经知道要选择哪些项目,则可以在item_tag表中的item_id上创建索引并使用第一个解决方案。如果平均而言,每个项目都有很多标签,这将节省您在item_tag表中查找大量行。否则,如果您太担心传输的数据量并且需要所有项目的结果,那么解决方案3似乎是合适的,因为将传输最少量的数据,但必须在客户端实现连接逻辑。所以,没有最好的解决方案。这一切都取决于具体情况。