0

使用Linq2db并且Ms Access我想选择所有没有目标的扇区,因此我想执行带有排除的左外连接:

Dim q10 = From s In db.Sectors
          From t In db.Targets.Where(Function(f) f.id_sector = s.Id).DefaultIfEmpty
          Where t Is Nothing
          Select s

Linq2db将此解决为:

--  Access
SELECT
    [t2].[Id],
    [t2].[Name]
FROM
    [tblSector] [t2]
        LEFT JOIN [tblTarget] [t1] ON ([t1].[id_sector] = [t2].[Id])
WHERE
    [t1].* IS NULL <=========== HERE

这显然是错误的。

我也试过:

Dim q10 = From s In db.Sectors
          From t In db.Targets.Where(Function(f) f.id_sector = s.Id And f Is Nothing).DefaultIfEmpty
          Select s

接收:

--  Access
SELECT
    [t2].[Id],
    [t2].[Name]
FROM
    [tblSector] [t2]
        LEFT JOIN [tblTarget] [t1] ON ([t1].[id_sector] = [t2].[Id] AND [t1].* IS NULL) <=========== HERE

总结一下,我需要:

SELECT
    [t2].[Id],
    [t2].[Name]
FROM
    [tblSector] [t2]
        LEFT JOIN [tblTarget] [t1] ON ([t1].[id_sector] = [t2].[Id])
WHERE
    [t1].[id_sector] IS NULL

如何在条件下写入Where t1.id_sector Is Nothing(id_sector 是FK这样,Integer所以它不可能是Nothing.

4

1 回答 1

0

我找到了答案。这是一个小解决方法,但它有效。

因为此查询不适用于linq2db

Dim q10 = From s In db.Sectors
          From t In db.Targets.Where(Function(f) f.id_sector = s.Id).DefaultIfEmpty
          Where t Is Nothing
          Select s

相反,我们可以这样写:

Dim q10 = From s In db.Sectors 
          Where Not (From t In db.Targets Select t.id_sector).Contains(s.Id)
          Select s

但是生成的 SQL 看起来像这样:

SELECT
    [t2].[Id],
    [t2].[Name]
FROM
    [tblSector] [t2]
        LEFT JOIN [tblTarget] [t1] ON ([t1].[id_sector] = [t2].[Id])
WHERE
    [t1].[id_sector] IS NULL

它看起来像这样:

SELECT
    [t2].[Id],
    [t2].[Name]
FROM
    [tblSector] [t2]
WHERE
    NOT (EXISTS(
        SELECT
            *
        FROM
            [tblTarget] [t1]
        WHERE
            [t1].[id_sector] = [t2].[Id]
    ))
于 2018-02-05T16:34:00.930 回答