【问题标题】:Aggregating Boolean Data in Access在 Access 中聚合布尔数据
【发布时间】:2014-05-16 13:27:03
【问题描述】:

是否有一种可接受/更好的方法在 Access 查询中聚合布尔数据?

我有两个相关的表,第一个表包含第二个数据的分组摘要。第二个表中的一个字段是一个布尔值是/否标志,指示该行需要“注意”。

我打算对第二个表的行执行 OR 并将结果存储在第一个表中,以指示表 2 中的“至少一个”相关行需要“注意”。

我看到 Access 将 False 存储为 0,将 True 存储为 -1,因此刚刚使用了 SUM/GROUP BY,似乎已经达到了我的目标。每个 True 值 (-1) 求和并给我一个负数,Access 似乎很乐意将其解释为 True。但是我注意到似乎没有任何方法可以执行 AND 操作(乘法?),这让我觉得我正在使用的这种方法有点像 hack,可能会产生一些意想不到的后果。

【问题讨论】:

  • 请提供您的 SQL 代码示例?
  • 您可以将逻辑表达式 MyAnd: [fieldA] AND [fieldB] 添加到查询中,然后可以像使用布尔值一样进行汇总。

标签: sql ms-access ms-access-2010


【解决方案1】:

为什么不直接使用 Sum(-MyFlag) 并将其与 Count(*) 进行比较?然后您可以测试两个数字是否相等。

【讨论】:

  • 这实际上会给你一个 AND 不是吗? Sum(-MyFlag) = Count(*) Sum(-MyFlag) > 0
  • 这里有导致某种溢出的危险吗?我想我对在对布尔值求和后最终会得到哪种数据类型有点困惑。例如,它会将结果“自动转换”为整数还是长整数?
【解决方案2】:

虽然 Access 数据库在内部将 Yes/No 值分别存储为 -1 和 0 是正确的,但最好的做法是使用适合其实际类型的方法来处理列,而不是依赖于基于其底层的“快捷方式”内部价值观。例如,最好使用DateAdd()DateDiff() 函数,而不是像[Date1]+30[Date2]-[Date1] 这样的事情。

因此,对于布尔值,我建议使用 Sum(IIf([NeedsAttention]=True,1,0)) 来计算 [NeedsAttention]=True 的行数。

【讨论】:

  • 为什么?我不认为理解字段的值并使用它应该是不好的做法。
  • @Remou 至少有两个原因:(1) 理解一定要完整。布尔值相当简单,但混淆日期/时间Double 值可能会真的变得复杂(参考:here)。 (2) 事情可能会改变。如果有一天True 变成 1 会怎样?或其他一些非零值?写入底层存储有点像过去糟糕的代码绕过操作系统并直接操纵硬件。它可以正常工作,直到某些东西(可能是非常微妙的东西)发生变化。
  • 如果您使用 SQL Server 后端,通常使用 smallint 比使用 boolean 更好,因此 true 为 1,但 sum(1) 和 sum(-1) 将始终为 总和(0)。 Access 分为 Jet/ACE 和 RAD 两部分。如果您使用的是 Jet/ACE,那么了解基础数据至关重要。
  • @Remou 我可以理解关于了解底层存储的论点。就我而言,我很有可能最终将此数据库转移到 SQL 后端。通常,我更愿意尝试为我的 SQL 编写最“通用”的代码(在我的能力范围内),这样如果我迁移到另一个平台,我就不必重新编写所有代码。 IIF() 有一些吸引我的地方,因为它明确地将布尔值转换为数字。虽然这可能只是我的偏执狂。
猜你喜欢
  • 1970-01-01
  • 2020-01-05
  • 2011-05-08
  • 1970-01-01
  • 2022-12-22
  • 2011-04-12
  • 1970-01-01
  • 2021-06-18
  • 2013-05-27
相关资源
最近更新 更多