Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/351.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/5/sql/79.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Java 如何使用jooq“在(…)中选择某个内容”?_Java_Sql_Jooq - Fatal编程技术网

Java 如何使用jooq“在(…)中选择某个内容”?

Java 如何使用jooq“在(…)中选择某个内容”?,java,sql,jooq,Java,Sql,Jooq,我正试图对Jooq进行以下操作,但我一辈子都不知道如何正确操作: select name, id in ( select capability_id from a.capabilities_users where user_id = ?) from a.capabilities; 基本上,我希望获得所有项的功能,并知道每个项是否适用于特定的用户。似乎所有条件类型运算符(如大于或in)只能在where中使用,而不能在select中使用。我想不出还有什么别的办法来表达这一点

我正试图对Jooq进行以下操作,但我一辈子都不知道如何正确操作:

select name, id in (
  select capability_id 
   from a.capabilities_users 
   where user_id = ?) 
from a.capabilities;
基本上,我希望获得所有项的功能,并知道每个项是否适用于特定的用户。似乎所有条件类型运算符(如大于或in)只能在where中使用,而不能在select中使用。我想不出还有什么别的办法来表达这一点


最糟糕的情况是,我可以先进行选择计数,然后在Java中执行布尔逻辑,但我希望使用fetchMap。

根据您的数据库和模式元数据,左连接可能比投影中的谓词更好。当然,您应该在执行计划中对此进行验证

使用左联接解决此问题: -NVL2是Oracle语法。 -如果数据库中没有NVL2,jOOQ将使用CASE模拟它 选择c.name,NVL2cu.capability\u id,1,0 来自a.c 左外连接a.U用户cu 在c.id=cu.capability\u id上 和cu.user_id=? 当然,以上假设cuuser_id、capability_id上存在unqiue约束。这将转化为jOOQ,如下所示:

能力c=能力.asc; CapabilitiesUsers cu=能力\用户.ascu; 字段键=c.NAME.askey; 字段值=nvl2 能力\用户能力\ ID,true,false .asvalue; 地图= DSL.usingconfiguration .选择键,选择值 .弗洛姆 .leftOuterJoincu .onc.ID.eqcu.CAPABILITY\u ID .和CU.用户ID.等式。。。 .fetchMapkey,值; 使用投影中的谓词解决此问题: 如果您确实喜欢投影中的谓词,您可以尝试,这正好允许:

Field<String> key = CAPABILITIES.NAME.as("key");
Field<Boolean> value = field(
  CAPABILITIES.ID.in(
    select(CAPABILITY_ID)
   .from(CAPABILITIES_USERS)
   .where(CAPABILITIES_USERS.USER_ID.eq(...))
  )
).as("value");

Map<String, Boolean> map =
DSL.using(configuration)
   .select(key, value)
   .from(CAPABILITIES)
   .fetchMap(key, value);

请注意,如果您使用的是符合标准的数据库,而该数据库不允许将谓词视为列,则会为您呈现一个等效的CASE语句。

您使用jOOQ的数据库是什么?大多数数据库不允许在投影中使用谓词,所以我怀疑这可能是PostgreSQL?@LukasEder:这种语法在Postgres中也是无效的。我认为SQL就是一个例子,它肯定是无效的SQL@a_horse_with_no_name:与PostgreSQL配合使用。事实上,根据集成测试的经验,我可以说它将与Derby、H2、HSQLDB、MariaDB、MySQL、PostgreSQL和SQLite@LukasEder:我站直了;谢谢你的例子,一个人真的从未停止学习…哇,我不知道我在做什么异国情调。有趣的博客帖子:顺便说一句,我正在使用PostgreSQL。我喜欢它。也真的很爱jOOQ!在我看来,一个好的查询优化器应该能够将select查询中的谓词重写为联接。Postgresql通常非常擅长于查询重写,但我会先对其进行解释,然后再假设它会这样做。@EricS:您可能认为Postgresql在这方面做得很好。特别是,如果c.ID和cu.UER_ID除了索引之外都没有空约束,那么合并联接可能会非常快。