从自然连接中排除列

时间:2018-04-05 09:48:05

标签: sql postgresql join natural-join

我目前有以下PostgreSQL DB(图片仅包含必要组件): DBVis image

基本上: 每个TX都有一些TXIN和一些TXOUT,每个TXIN包含一个TXOUT的RING(Monero事务)

如果我使用ring表加入txin表,我使用select * from ring natural join txin并使用inid进行加入。 ringtxout相同,但它加入outid

txintxout也可以使用自然联接tx加入,以获得合理的输出。

(预期)唯一不起作用的是:

select * from txout natural join ring natural join txin;

因为它会加入ring(inid) = txin(inid)ring(outid) = txout(outid)(这是所需的),但也加入txin(txid) = txout(txid)这是不可取的。

我有一些想法如何解决这个问题:

  1. 使用显式连接(在我看来,使一些查询非常麻烦),例如以上将是:select * from txout join ring using (outid) join txin using (inid);

  2. 重命名txin或txout中的两个txid列之一,并放弃使用tx的自然连接

  3. 使用省略txid的txin / txout视图进行这些操作

  4. 还有其他(更好)的方式吗?如果不是 - 哪种方法最佳实践? 我的数据库设计是否缺乏,整个问题可以以某种方式被规避?

2 个答案:

答案 0 :(得分:2)

自然连接被明确定义为连接所有具有相同名称的列。这就是它的实际情况,它与(如果此语法有效)JOIN table USING (*)实际上相同。 详细SQL 没有任何问题。在你的加入条件下非常清楚它是更好,更易于维护的,并且它意味着如果你将来在这些表中添加一列它不会弄乱历史数据。在这种情况下,我建议使用显式语法加入,因为这样可以清楚地显示数据的来源:

SELECT * 
FROM txout to
INNER JOIN ring r ON (to.outid = r.outid)
INNER JOIN txin ti ON (r.inid = ti.inid)

这里要清楚。自然连接不是一个可维护的解决方案,它们非常适合将视图混合在一起,但模式更改,如果您在显式连接上使用自然连接,则会遇到问题。

我不确定您为什么设计数据库的方式,看起来数据有意重叠,可以全部放在(txid, inid, outid, txhash)的单个表中,但也许我缺乏完整的背景。

答案 1 :(得分:0)

我建议使用简化的Oracle语法:

SELECT * 
  FROM ring
  JOIN txout USING(outid)
  JOIN txin  USING(inid)