有没有办法寻找改变位置的无序值?
Posted
技术标签:
【中文标题】有没有办法寻找改变位置的无序值?【英文标题】:Is there a way to look for unordered values that change position? 【发布时间】:2021-10-09 01:36:47 【问题描述】:有一个包含 50 列的表,它们都包含从 1 到 99 的数字。如果我想搜索,例如8,36,52不管在哪里,只要在同一个元组里,我会做吗?我被卡住了,因为如果我指定列,我会限制搜索。拜托,欢迎任何帮助!
【问题讨论】:
根据问题指南,请展示您尝试过的内容并告诉我们您发现了什么(在本网站或其他地方)以及为什么它不能满足您的需求。另请提供minimal reproducible example,包括样本数据、所需结果和您的尝试。where (c1=8 or c2=8 or c3=8...) and (c1=36 or c2=36 or c3=36...) and (c1=52 or c2=52 or c3=52...)
?
基本上,如果您有 50 列数字如此难以区分,以至于集体搜索它们以查找匹配的数字是有意义的,而不管它们分配的列,那么您就有了一个糟糕的(非关系)数据设计。您有时可以证明跨列搜索文本子字符串是合理的,但很少会搜索数字:它们应该被设计为一开始就在一个列中。
【参考方案1】:
这将动态地 UNPIVOT 行,而不必使用动态 SQL
示例或dbFiddle
Declare @Search varchar(50)='8,36,52';
with cte as (
Select Distinct Value From string_split(@Search,',')
)
Select A.*
From YourTable A
Cross Apply (
Select Hits =Count(Distinct B1.Value)
From OpenJson((Select A.* For JSON Path,Without_Array_Wrapper )) B1
Join cte B2 on B1.Value=B2.Value
) B
Where Hits = ( select count(*) from cte )
【讨论】:
【参考方案2】:这是另一种基于 XML/XQuery 的方法。
它使用 XQuery 的 量化表达式。
Quantified Expressions (XQuery)
给定两个序列,如果第一个序列中的每个项目在第二个序列中都有匹配,则返回值为 True。正是我们需要的。
CTE 中的 XML 对于每一行如下所示:
<root>
<source>
<r>8</r>
<r>36</r>
<r>52</r>
</source>
<target>
<ID>1</ID>
<Col1>0</Col1>
<Col2>15</Col2>
<Col3>45</Col3>
<Col4>7</Col4>
<Col5>88</Col5>
<Col6>22</Col6>
</target>
</root>
SQL
-- DDL and data population, start
DECLARE @tbl TABLE
(
ID INT IDENTITY PRIMARY KEY,
[Col1] INT,
[Col2] INT,
[Col3] INT,
[Col4] INT,
[Col5] INT,
[Col6] INT
);
INSERT INTO @tbl
VALUES
(0, 15, 45, 7, 88, 22),
(1, 36, 8, 7, 14, 52),
(32, 36, 36, 1, 1, 1); -- Duplicate Values
-- DDL and data population, end
DECLARE @Search VARCHAR(50) = '8,36,52'
, @separator CHAR(1) = ',';
;WITH rs AS
(
SELECT *
, TRY_CAST('<root>' +
'<source><r><![CDATA[' + REPLACE(@Search, @separator, ']]></r><r><![CDATA[') +
']]></r></source>' +
(SELECT * FROM @tbl AS c
WHERE p.ID = c.ID
FOR XML PATH(''), ROOT('target')) +
'</root>' AS XML)
.query('every $x in /root/source/r/text()
satisfies ($x = (/root/target/*[local-name()!="ID"]/text()))')
.value('text()[1]', 'bit') result
FROM @tbl AS p
)
SELECT * FROM rs
WHERE rs.result = 1;
【讨论】:
以上是关于有没有办法寻找改变位置的无序值?的主要内容,如果未能解决你的问题,请参考以下文章
有没有办法让 UIScrollView 在任意位置停止和反弹