我有以下架构:
CREATE TABLE products (
id BIGSERIAL NOT NULL,
created_at_timestamp TIMESTAMP NOT NULL DEFAULT NOW(),
last_update_timestamp TIMESTAMP NOT NULL DEFAULT NOW(),
PRIMARY KEY (id)
);
CREATE TABLE product_names (
product_id BIGINT NOT NULL,
language TEXT NOT NULL,
name TEXT NOT NULL,
PRIMARY KEY (product_id, language),
FOREIGN KEY (product_id) REFERENCES products (id)
);
CREATE TABLE product_summaries (
product_id BIGINT NOT NULL,
language TEXT NOT NULL,
summary TEXT NOT NULL,
PRIMARY KEY (product_id, language),
FOREIGN KEY (product_id) REFERENCES products (id)
);
我想select
所有产品。
但是,您会看到产品包含名称和摘要(每种语言)的列表。
我可以检索所有产品
SELECT * FROM products
然后迭代所有行(在本例中为Kotlin),然后请求名称和摘要:
SELECT * FROM product_names WHERE product_id = $id
和
SELECT * FROM product_summaries WHERE product_id = $id
但是,这似乎效率低下,因为我要对数据库进行3个单独的查询。
我虽然使用JOIN
来通过一个查询来获取所有这些信息,但是随后我为每个product_names
和product_summaries
条目获得了多个重复的行。
最后,有没有更好的方法可以在一个查询中请求所有这些数据?
答案 0 :(得分:1)
您绝对不想执行多个查询,然后在代码中对其进行迭代。效率低下。当您执行第二个07-19 14:29:52.971 9123-9390/com.packaename.abc E/Unity: AndroidJavaException: java.lang.ClassNotFoundException: io.fabric.unity.android.FabricInitializer
java.lang.ClassNotFoundException: io.fabric.unity.android.FabricInitializer
at java.lang.Class.classForName(Native Method)
at java.lang.Class.forName(Class.java:324)
at java.lang.Class.forName(Class.java:285)
at com.unity3d.player.UnityPlayer.nativeRender(Native Method)
at com.unity3d.player.UnityPlayer.c(Unknown Source)
at com.unity3d.player.UnityPlayer$c$1.handleMessage(Unknown Source)
at android.os.Handler.dispatchMessage(Handler.java:107)
at android.os.Looper.loop(Looper.java:207)
at com.unity3d.player.UnityPlayer$c.run(Unknown Source)
Caused by: java.lang.ClassNotFoundException: Didn't find class "io.fabric.unity.android.FabricInitializer" on path: DexPathList[[zip file "/data/app/com.packaename.abc-1/base.apk"],nativeLibraryDirectories=[/data/app/com.packaename.abc-1/lib/arm, /data/app/com.packaename.abc-1/base.apk!/lib/armeabi-v7a, /vendor/lib, /system/lib]]
at dalvik.system.BaseDexClassLo
时,您需要在JOIN
中包含language
。那应该使您避免重复行。对于[products.id,product_names.language]
JOIN
答案 1 :(得分:0)
我找到了一种方法:
SELECT * FROM products as p INNER JOIN
(SELECT json_agg(product_names) as names, product_id FROM product_names GROUP BY product_id) as tb_names ON tb_names.product_id = p.id
INNER JOIN
(SELECT json_agg(product_summaries) as summaries, product_id FROM product_summaries GROUP BY product_id) as tb_summaries ON tb_summaries.product_id = p.id
返回:
1 | 2018-07-20 09:36:21.56904 | 2018-07-20 09:36:21.56904 | [{"product_id":1,"language":"EN","name":"lol"},
{"product_id":1,"language":"DE","name":"lel"}] | 1 [{"product_id":1,"language":"EN","summary":"deded"},
{"product_id":1,"language":"DE","summary":"rererere"},
{"product_id":1,"language":"FR","summary":"jejejeje"}] | 1
基本上我正在将多维表转换为JSON:)
Postgres很棒!