MS Access 中的加入或子查询

Posted

技术标签:

【中文标题】MS Access 中的加入或子查询【英文标题】:Join or subquery in MS Access 【发布时间】:2011-01-07 19:32:44 【问题描述】:

我在开始时查看了“相关问题”,但没有一个与我正在尝试做的完全一样。

如果可能的话,我希望我的查询是可更新的。

哪个更好?

SELECT foobar.foo, foobar.bar
FROM foobar
WHERE foobar.baz IN (SELECT blahwoof.baz FROM blahwoof WHERE blahwoof.blah = 'value')

或者:

SELECT foobar.foo, foobar.bar
FROM foobar INNER JOIN blahwoof ON foobar.baz = blahwoof.baz
WHERE blahwoof.blah = 'value'

编辑

我已经完全限定了上面的列名。我还意识到我没有完全指定我只关心更新 foobar --blahwoof 只是一个查找表。

编辑 2

基本架构如下(显然不是实际代码):

table foobar
  foo       Autonumber PK
  bar       long       FK ref gleeblesnort
  baz       long       FK ref blahwoof

table blahwoof
  baz       Autonumber PK
  blah      text       --'type' designation

我最终也会从 gleeblesnort 中提取值,但这不是此查询的直接部分。

【问题讨论】:

【参考方案1】:

视图的第一个版本可以在任何合理兼容的 SQL RDBMS 中更新。

【讨论】:

这个特定示例的 JOIN 版本也应该是可更新的。我敢肯定,您的观点是 IN 子查询将比 JOIN 版本更频繁地更新,特别是如果查询优化器无法确定 JOIN 语句返回的确切记录数。 @David,老实说,我最初有第二段解释如何以及为什么要在 Access 中更新此视图。但我发现我错了(我不知何故明白了它需要 DISTINCTROW),所以我把它拿出来并留下了第一段。 DISTINCTROW 可以使一些没有它时只读的 SELECT 语句可编辑,但是很难预测它什么时候可以工作,什么时候不可以。这完全取决于不可编辑性的原因。基本上,如果问题是 Jet 无法计算出连接的每一侧有多少行,则 DISTINCTROW 通常能够使其可编辑(尽管并非总是如此)。但是,如果不可编辑的原因是由于域聚合或 JOINed SELECT 之一中的 GROUP BY,则 DISTINCTROW 将不起作用。 接受了,因为我已经使用了子查询,尽管这两种方式的答案似乎都没有达成一致。测试表明每个都可以工作,在我的(诚然很小的)样本数据中没有可检测到的性能差异。【参考方案2】:

使用内连接。它应该性能更高。 IIRC,这也将是可更新的。

【讨论】:

答案取决于SQL语句。如果 JOIN 版本是可更新的,它可能会更快。如果不是并且您需要可更新性,那么 IN 子查询是更好的版本。但这实际上只与绑定的 Access 表单(非常相关)或在遍历和编辑记录集时相关。 它将在绑定表单上,但是——正如我在编辑中所说——实际上只有 foobar.bar 需要更新。 我认为我的回答有点草率,因为@David 让我开始思考。了解更多有关架构的信息会很好 - PK、FK、唯一索引......内部连接可以多次返回 foobar 行,其中 blahwoof.baz 不是唯一的。【参考方案3】:

我认为它们不是同一个查询。在第一个查询中,如果您有 1 个 baz 值,则足以满足 WHERE 条件,并且您实际上是指连接结果(baz 和 blah=value...)

(您可能需要使用 baz 的表前缀信息以使其更清晰)

【讨论】:

每个表中有一个bazblahwoof 中有几行。这是唯一的共同点。见编辑。

以上是关于MS Access 中的加入或子查询的主要内容,如果未能解决你的问题,请参考以下文章

MS Access 中的子查询问题

如何加入 MS Access 中的功能?

更新查询 MS Access 加入

基于包含子查询的查询的 ms-access 交叉表查询

MS Access SQL 查询 - 加入错误

使用包含 SUM() 字段的子查询在 MS-Access 中编辑查询