查找多次引用的表中的所有外键行

时间:2010-12-22 15:41:01

标签: sql

我有以下数据库结构:

CREATE TABLE LookupTable
(
    PK UNIQUEIDENTIFIER PRIMARY KEY,
)

CREATE TABLE MainTable
(
    Lookup1 UNIQUEIDENTIFIER FOREIGN KEY REFERENCES LookupTable(PK),
    Lookup2 UNIQUEIDENTIFIER FOREIGN KEY REFERENCES LookupTable(PK),
    -- ...
    -- ... LookupN UNIQUEIDENTIFIER FOREIGN KEY REFERENCES LookupTable(PK),
)

MainTable通过单独的列多次引用LookupTable。

如果我插入以下数据:

INSERT INTO LookupTable VALUES('11111111-1111-1111-1111-111111111111')
INSERT INTO LookupTable VALUES('22222222-2222-2222-2222-222222222222')
INSERT INTO MainTable VALUES('11111111-1111-1111-1111-111111111111','22222222-2222-2222-2222-222222222222')
INSERT INTO MainTable VALUES('22222222-2222-2222-2222-222222222222','11111111-1111-1111-1111-111111111111')

我希望能够在[MainTable]中查找任何查找字段等于'11111111-1111-1111-1111-111111111111'的所有记录(这应该返回示例中的两行)。

SQL不是我的强项。有没有比

更简单的方法
SELECT * FROM MainTable WHERE
Lookup1 = '11111111-1111-1111-1111-111111111111'
OR
Lookup2 = '11111111-1111-1111-1111-111111111111'
-- ...
-- OR
-- LookupN = '11111111-1111-1111-1111-111111111111'

这看起来很乏味,因为它需要我按名称指定每个查阅列,然后才能检索到我想要的结果。在我的数据库中,在某些情况下可以有20多个查找列。

2 个答案:

答案 0 :(得分:4)

有三种选择:

  • 按照您的方式查询表格(许多OR)
  • 动态构建查询并执行它(如SQL Server上的EXEC)
  • 更改数据库架构并将Lookup-columns从MainTable移动到第三个表

CREATE TABLE LookupTable
(
    PK UNIQUEIDENTIFIER PRIMARY KEY,
)


CREATE TABLE MainTable
(
    PK UNIQUEIDENTIFIER PRIMARY KEY,
)

CREATE TABLE MainTableLookup
(
    MainTablePK UNIQUEIDENTIFIER FOREIGN KEY REFERENCES MainTable(PK),
    Lookup UNIQUEIDENTIFIER FOREIGN KEY REFERENCES LookupTable(PK),
)

然后你可以像这样查询:

SELECT
    * 
FROM 
    MainTable MT JOIN MainTableLookup ON MT.PK = MTL.MainTablePK
WHERE
    EXISTS (SELECT 1 FROM LookupTable LT 
            WHERE LT.PK = MTL.Lookup
                  AND MTL.Lookup = '11111111-1111-1111-1111-111111111111')

答案 1 :(得分:0)

另一个建议。使用OR进行查询可能会导致性能下降;使用UNION可以更快:

SELECT * FROM MainTable WHERE
Lookup1 = '11111111-1111-1111-1111-111111111111'
UNION
SELECT * FROM MainTable WHERE
Lookup2 = '11111111-1111-1111-1111-111111111111'
...