Java 复杂的SQL where子句-集体选择所有但从不重叠

Java 复杂的SQL where子句-集体选择所有但从不重叠,java,sql,set,Java,Sql,Set,编辑:我的问题有缺陷,因为它被误解了。我正在重新措辞。原始问题位于人力资源部下方,供好奇者参考 给定几个对相同数据进行操作的SQL查询,如何在类型系统、对象模型或测试代码中断言每个可能的行都是由一个查询选择的: i、 e.在这个维恩图中,感谢@Imre_L的图片,什么是断言查询A、B和U不重叠的最佳方式 请注意,问题空间是所有可能的数据,而不仅仅是现有的数据集 原来的问题 我正试图设计一种安全且易于理解的机制来组成一组where子句,其中所选行的子集从不重叠,但执行所有子句将选择所有行的集合 例

编辑:我的问题有缺陷,因为它被误解了。我正在重新措辞。原始问题位于人力资源部下方,供好奇者参考

给定几个对相同数据进行操作的SQL查询,如何在类型系统、对象模型或测试代码中断言每个可能的行都是由一个查询选择的:

i、 e.在这个维恩图中,感谢@Imre_L的图片,什么是断言查询A、B和U不重叠的最佳方式

请注意,问题空间是所有可能的数据,而不仅仅是现有的数据集

原来的问题

我正试图设计一种安全且易于理解的机制来组成一组where子句,其中所选行的子集从不重叠,但执行所有子句将选择所有行的集合

例如,给定伪SQL中的一个子句,如:

... where name like 'Bob%'
and surname not like '%Smith' 
and postcode in (2000, 2010, 2020)
还有一个

... where name in ('Alice', 'Jane')
and postcode < 9000
and married=True
和最后一个查询来捕获剩余部分

... where not (name like 'Bob%' and surname not like '%Smith' and postcode in (2000, 2010, 2020))
and not (name in ('Alice', 'Jane') and postcode < 9000 and married=True)
我如何断言每个可能的行恰好由一个可能的查询选择

我的团队正在慢慢地将行为从系统的一个部分迁移到另一个部分,并需要在每个阶段更改语句集,以便在更改后由一条语句选择的某些行由另一条语句选择。在每次更改之前和之后,上面的断言都需要保持true

我正在寻找一个简洁的Java解决方案。无论它是在类型系统中检查的,还是由某些创建模式控制的,甚至是在测试期间检查的,都无关紧要。我肯定有些学者有一些好主意。

这是错误的-问题是所有可能的数据

我不确定我是否理解,但SQL包含union和distinct,因此您可以检查计数:

所有查询联合在一起

所有查询联合在一起,不同的行

表中的所有行

他们应该是平等的。如果您完全缺少一行,那么2将小于3;如果在任何位置复制行,则2将小于1

1和2的查询将是:

select count(*) from (
  select ....
  union [distinct]
  select ...
  union [distinct]
  ...)
这是错误的——问题在于所有可能的数据

我不确定我是否理解,但SQL包含union和distinct,因此您可以检查计数:

所有查询联合在一起

所有查询联合在一起,不同的行

表中的所有行

他们应该是平等的。如果您完全缺少一行,那么2将小于3;如果在任何位置复制行,则2将小于1

1和2的查询将是:

select count(*) from (
  select ....
  union [distinct]
  select ...
  union [distinct]
  ...)

这道题更像是一道数学题,是集合论。也许维恩图是来拯救的

在您的示例中,A和B是查询1,2,U是最后一个查询

了解更多关于


如果你希望得到更好的答案,你应该详细说明

这个问题更像是一个数学问题,它是集合论。也许维恩图是来拯救的

在您的示例中,A和B是查询1,2,U是最后一个查询

了解更多关于


如果你希望得到更好的答案,你应该详细说明

我用手工制作的方法在自动化测试中解决了这个问题

我列举了各种查询中涉及的列,以及每个列的不同where子句条件。 然后,我创建了这些的笛卡尔积,并在测试设置中为它们创建了一个insert语句。 最后,我执行了每个DAO方法,并断言@andrew cooke答案中的属性是正确的。
我更希望采用一种真正自动化的方法,包括一个奇特的类型层次结构,但我们不能总是得到我们想要的。

我用手工制作的方法在自动化测试中解决了这个问题

我列举了各种查询中涉及的列,以及每个列的不同where子句条件。 然后,我创建了这些的笛卡尔积,并在测试设置中为它们创建了一个insert语句。 最后,我执行了每个DAO方法,并断言@andrew cooke答案中的属性是正确的。
我更希望采用一种真正自动化的方法,包括一个奇特的类型层次结构,但我们不能总是得到我们想要的。

什么是“伪SQL”?你是说查询不是在SQL中,而是在其他地方?您需要一个Java解决方案。这是一个带有查询API的Java内存数据库吗?我们缺少了很多可以理解这个问题的上下文。“伪SQL”就是伪SQL。这不是一个专有名词。它类似于伪代码,但它是SQL。数据库供应商与此无关,也与它是否在内存中无关。这个问题的本质是关于如何通过计算组合复杂的select子句;或者测试手工制作的子句的属性。那么,如何组合查询完全取决于您可用的功能。在SQL中很难表达的东西在另一种查询语言中可能很容易表达。@Synesso你是在问这个问题怎么解决

考虑到可用的工具集,m可以解决吗?e、 Java和SQL什么是“伪SQL”?你是说查询不是在SQL中,而是在其他地方?您需要一个Java解决方案。这是一个带有查询API的Java内存数据库吗?我们缺少了很多可以理解这个问题的上下文。“伪SQL”就是伪SQL。这不是一个专有名词。它类似于伪代码,但它是SQL。数据库供应商与此无关,也与它是否在内存中无关。这个问题的本质是关于如何通过计算组合复杂的select子句;或者测试手工制作的子句的属性。那么,如何组合查询完全取决于您可用的功能。有些很难用SQL表达的东西在另一种查询语言中可能很容易。@Synesso您是否在问,在现有的工具集下,如何解决这个问题?e、 Java和sql谢谢。现在给出三个SQL查询,断言它们满足此约束。这是我的问题。举个例子很简单:A:name像'Bob%'和B:name在'Alice','Jane'中,这使得它们不重叠,U只是不是A,不是yes,而是用它来做一个可执行的断言。i、 如果我把它改成A:像“Bob%”这样的名字,B:像“Alice”、“Jane”、“Bobby”这样的名字,我的构建会失败吗?谢谢。现在给出三个SQL查询,断言它们满足此约束。这是我的问题。举个例子很简单:A:name像'Bob%'和B:name在'Alice','Jane'中,这使得它们不重叠,U只是不是A,不是yes,而是用它来做一个可执行的断言。i、 如果我把它改成A:像“Bob%”这样的名字,B:像“Alice”、“Jane”、“Bobby”这样的名字,我的构建会失败吗?谢谢。但是,我需要为所有可能的行断言,而不是所有现有行。好吧,那要难多了。。。您需要显示查询中的谓词一起唯一地跨越可能值的范围。我只是重复您所说的,真的。我不知道你将如何自动化,除非使用某种定理证明器,这远远超出了合理的范围。我将留下我的答案,因为你的评论可能有助于为其他人澄清。谢谢安德鲁。我认识到这是一个难题。如果事实证明它太难实际解决,那么我也会把它作为一个答案。我能想到的最好的答案是在测试时使用scalacheck之类的工具插入大量随机数据,然后使用上面包含的SQL语句执行断言。如果需要断言所有可能的行,这意味着可能还不存在的行,那么解决方案不能纯粹是数据驱动的。哎哟,汉克斯。但是,我需要为所有可能的行断言,而不是所有现有行。好吧,那要难多了。。。您需要显示查询中的谓词一起唯一地跨越可能值的范围。我只是重复您所说的,真的。我不知道你将如何自动化,除非使用某种定理证明器,这远远超出了合理的范围。我将留下我的答案,因为你的评论可能有助于为其他人澄清。谢谢安德鲁。我认识到这是一个难题。如果事实证明它太难实际解决,那么我也会把它作为一个答案。我能想到的最好的答案是在测试时使用scalacheck之类的工具插入大量随机数据,然后使用上面包含的SQL语句执行断言。如果需要断言所有可能的行,这意味着可能还不存在的行,那么解决方案不能纯粹是数据驱动的。哎哟