WHERE 子句中 AND 和 OR 的多个条件 SQL Server

问题描述 投票:0回答:2

我在 Microsoft SQL Server Management Studio 工作。我正在使用多个表和多个条件(近 80 个),我正在查询这些条件以尝试实现连接数据的子集。

这个想法是,我需要从连接中获取数据,其中该数据不在基于条件的不同连接中(即

NOT IN
),然后我需要过滤涉及多个列和多个的一堆条件每列的条件。我的问题(我认为)是由
OR
条件引起的。我有一列,比如
col5
,如果它不满足
AND
条件中的任何条件,那么我需要进一步过滤它(因此,
OR
条件)。

到目前为止我所写的内容如下,

SELECT 
    handfulOfColumns
FROM 
    table1 AS t1
LEFT JOIN
    (SELECT *
     FROM table2
     WHERE col2 = 'thing0' or col2 = 'thing1') AS t2 ON t1.col1 = t2.col1
WHERE 
    t1.col1 NOT IN (SELECT t1.col1
                    FROM table1 t1
                    LEFT JOIN table3 t3 ON t1.col1 = t3.col1
                    WHERE col3 LIKE '%thing3%')
    AND (col4 > '#' AND col5 NOT LIKE 'thing4' 
         AND col5 != 'thing5' AND col5 NOT LIKE 'thing6' 
         AND col6 NOT LIKE 'thing7'
         --...
         --... add like 20 lines of conditions similar to above
         --...
         AND col34 NOT LIKE 'thing77' AND LEN(col35) > '#')
     OR (col5 NOT LIKE '% %' AND col5 LIKE '%[a-z]%' 
         AND col5 NOT LIKE '%[0-9]%' 
         AND col5 NOT LIKE 'thing209' 
         AND col5 NOT LIKE 'thing210');

这样做的原因是我在

col5
中处理了很多(混乱的)电话号码,总体而言,所有列都需要进行大量清理。其中一些电话号码将输入文本,根据上下文,我可能希望保留它们或将其过滤掉(即电话号码输入为“公司名称”、“公司”或“alskfjalsdkjf”的情况) ,而不是“555-5555”或“555 5555”等)。如果数据满足
AND
条件的标准(主要是过滤掉
col5 not like '%555-5555%'
的变体),那么我需要通过
col5
条件进一步检查和过滤
OR
中的任何非数字字符。

没有错误消息 - 相反,查询需要很长时间才能完成,并且给我提供的数据行比开始时更多,这与应该发生的情况相反。基于

table1
table2
的结构,通过连接两个表有可能引入重复的行,但是我正在做的调节和子设置的数量应该远远少于原始的行数,甚至到处都有一些重复的内容。

我不确定我的逻辑在哪里失败,感谢任何帮助:)

sql-server conditional-statements where-clause
2个回答
0
投票

除了 marc_s 建议的正确语法修正之外,这实际上运行得很好。事实证明,我在

AND
条件下有几个条件语句不正确(即一些
=
,逻辑上它们应该是
!=
like
,它们应该是
not like
),但整体结构和逻辑是健全的 - 在几个测试数据库上重新运行并且它运行完美。如果这让任何人头疼,我深表歉意:)


0
投票

你的逻辑看起来很混乱,即使它提供了正确的结果。为了使查询更具可读性,我会尝试以下操作:

1)如果允许您向现有架构添加一些列,则可以添加一些可在查询中重用的有意义的列。你的桌子可能看起来像这样:

create table table1 
(
    Id INT NOT NULL,
    col1 VARCHAR(64),
    col2 VARCHAR(64),
    col3 VARCHAR(64),
    col4 VARCHAR(64),
    col5 VARCHAR(64),

    Thing4Like AS (CASE WHEN col4 > '#' AND col5 NOT LIKE 'thing4' THEN CAST(1 AS BIT) ELSE CAST(0 AS BIT) END) PERSISTED,
    Thing56 AS (CASE WHEN col5 != 'thing5' AND col5 NOT LIKE 'thing6' THEN CAST(1 AS BIT) ELSE CAST(0 AS BIT) END) PERSISTED
    -- other columns may come here
)

这允许您编写更具可读性的查询,甚至使查询速度更快,因为某些信息是预先计算的。此外,持久列允许索引。

2) 如果您无法更改架构,您可以在 table1 上创建一个包含额外逻辑的视图,如上所述。为了获得额外的性能,可以对它们进行索引

© www.soinside.com 2019 - 2024. All rights reserved.