sql 使用子字符串 charindex 查询

sql query with substring charindex

table1
::::::::::::::::::::::::::::::::::
id | id_data | id_t | value 
1  | 43      | 1    | 
2  | 46      | 1    | 111,112,113
3  | 43      | 2    | 
4  | 46      | 2    | 90,5

table2
:::::::::::::::::::::::::::::::::::
id_value | cat
112      | cat1
5        | cat2

嗨,如果可能的话,我需要一些帮助。

我需要更新 table1.value 其中 id_data 为 43 为 table2.cat 其中 id_value = 值 ',' 'till the next ' 之后的数字 如果'id_t'

中每个组都有

我尝试了一个简单的查询,但它返回了一些 null 但 'value' 不能为 null

update table1 
set value = (select cat from table2 
            where convert(nvarchar,id_value) = substring(value,5,3))
where id_data='43'

我一直在尝试合并 CHARINDEX 以从“,”中获取,但我就是无法弄清楚它是如何工作的。

理想情况下它应该是这样的:

::::::::::::::::::::::::::::::::::
id | id_data | id_t | value 
1  | 43      | 1    | cat1
2  | 46      | 1    | 111,112,113
3  | 43      | 2    | cat2
4  | 46      | 2    | 90,5

谁能给我指明正确的方向,好吗?

我想这很简单..但我还在学习...

提前致谢。

::::::::::::::::

更新 1

WITH UpdateableCTE AS
(
    SELECT t1.id
          ,t1.id_data
          ,t1.id_t
          ,SecondNr
          ,(
            SELECT t2.cat
            FROM @table2 AS t2 WHERE t2.id_value=SecondNr
           ) AS NewCat
           ,t1.value
    FROM @table1 AS t1
    OUTER APPLY(SELECT CAST('<x>' + REPLACE(x.value,',','</x><x>') + '</x>' AS XML).value('/x[2]','int')
                FROM @table1 AS x 
                WHERE x.id_t=t1.id_t AND x.value IS NOT NULL AND id_data='46') AS ID(SecondNr)
    WHERE t1.value IS NULL
)
UPDATE UpdateableCTE SET value=NewCat;
--somehow where id_data='43'

我将在此处留下一个 table,它看起来更接近真实的 id_data 和字段:

17974492    1   999251  somevalue
17974493    2   999251  somevalue
17974494    3   999251  somevalue
17974495    4   999251  somevalue
17974496    5   999251  somevalue
17974497    43  999251  (thishsouldbeupdated)
17974498    6   999251  somevalue
17974499    7   999251  somevalue
17974500    46  999251  111,311
17974501    8   999251  somevalue
17974502    9   999251  somevalue
17974503    10  999251  somevalue
17974504    11  999251  somevalue
17974505    12  999251  somevalue
17974506    13  999251  somevalue
17974507    1   999252  somevalue
17974508    2   999252  somevalue
17974509    3   999252  somevalue
17974510    4   999252  somevalue
17974511    5   999252  somevalue
17974512    43  999252  (thisshouldbeupdated)
17974513    6   999252  somevalue
17974514    7   999252  somevalue
17974515    46  999252  98,98
17974516    8   999252  somevalue
17974517    9   999252  somevalue
17974518    10  999252  somevalue
17974519    11  999252  somevalue
17974520    12  999252  somevalue
17974521    13  999252  somevalue

这不是干净的,也不是我推荐的东西,但你可能会找到一些帮助:

DECLARE @table1 TABLE(id INT,id_data INT,id_t INT,value VARCHAR(100));
INSERT INTO @table1 VALUES 
 (1,43,1,NULL)
,(2,46,1,'111,112,113')
,(3,43,2,NULL)
,(4,46,2,'90,5')

DECLARE @table2 TABLE(id_value INT,cat VARCHAR(100));
INSERT INTO @table2 VALUES
 (112,'cat1')
,(5,'cat2');

SELECT t1.id
      ,t1.id_data
      ,t1.id_t
      ,ID.List
      ,(
        SELECT t2.cat
        FROM @table2 AS t2 WHERE CHARINDEX(',' + CAST(t2.id_value AS VARCHAR(100)) + ',',',' + ID.List + ',')>0
       )
FROM @table1 AS t1
OUTER APPLY(SELECT x.value FROM @table1 AS x WHERE x.id_t=t1.id_t AND x.value IS NOT NULL) AS ID(List)
WHERE t1.value IS NULL

更新:您对使用第二个数字作为更新的解释

试试这个

DECLARE @table1 TABLE(id INT,id_data INT,id_t INT,value VARCHAR(100));
INSERT INTO @table1 VALUES 
 (1,43,1,NULL)
,(2,46,1,'111,112,113')
,(3,43,2,NULL)
,(4,46,2,'90,5')

DECLARE @table2 TABLE(id_value INT,cat VARCHAR(100));
INSERT INTO @table2 VALUES
 (112,'cat1')
,(5,'cat2');

WITH UpdateableCTE AS
(
    SELECT t1.id
          ,t1.id_data
          ,t1.id_t
          ,SecondNr
          ,(
            SELECT t2.cat
            FROM @table2 AS t2 WHERE t2.id_value=SecondNr
           ) AS NewCat
           ,t1.value
    FROM @table1 AS t1
    OUTER APPLY(SELECT CAST('<x>' + REPLACE(x.value,',','</x><x>') + '</x>' AS XML).value('/x[2]','int')
                FROM @table1 AS x 
                WHERE x.id_t=t1.id_t AND x.value IS NOT NULL) AS ID(SecondNr)
    WHERE t1.value IS NULL
)
UPDATE UpdateableCTE SET value=NewCat;

SELECT * FROM @table1

概念是可更新的 CTE,您可以在其中使用普通 SELECT 来获取所需的值。然后,您可以直接更新派生的 table(只要只有一个 table 的列受影响)。

OUTER APPLY 使用 XML 的技巧来拆分 CSV 列表以读取第二个数字。

更新 2:使用您的新示例数据

以下将使用新示例数据并使用 ID:

DECLARE @table1 TABLE(id INT,id_data INT,id_t INT,value VARCHAR(100));
INSERT INTO @table1 VALUES 
 (17974492,1,999251,'somevalue')
,(17974493,2,999251,'somevalue')
,(17974494,3,999251,'somevalue')
,(17974495,4,999251,'somevalue')
,(17974496,5,999251,'somevalue')
,(17974497,43,999251,'(thishsouldbeupdated)')
,(17974498,6,999251,'somevalue')
,(17974499,7,999251,'somevalue')
,(17974500,46,999251,'111,311')
,(17974501,8,999251,'somevalue')
,(17974502,9,999251,'somevalue')
,(17974503,10,999251,'somevalue')
,(17974504,11,999251,'somevalue')
,(17974505,12,999251,'somevalue')
,(17974506,13,999251,'somevalue')
,(17974507,1,999252,'somevalue')
,(17974508,2,999252,'somevalue')
,(17974509,3,999252,'somevalue')
,(17974510,4,999252,'somevalue')
,(17974511,5,999252,'somevalue')
,(17974512,43,999252,'(thisshouldbeupdated)')
,(17974513,6,999252,'somevalue')
,(17974514,7,999252,'somevalue')
,(17974515,46,999252,'98,98')
,(17974516,8,999252,'somevalue')
,(17974517,9,999252,'somevalue')
,(17974518,10,999252,'somevalue')
,(17974519,11,999252,'somevalue')
,(17974520,12,999252,'somevalue')
,(17974521,13,999252,'somevalue');

DECLARE @table2 TABLE(id_value INT,cat VARCHAR(100));
INSERT INTO @table2 VALUES
 (311,'cat1')
,(98,'cat2');

WITH UpdateableCTE AS
(
    SELECT t1.id
          ,t1.id_data
          ,t1.id_t
          ,SecondNr
          ,(
            SELECT t2.cat
            FROM @table2 AS t2 WHERE t2.id_value=SecondNr
           ) AS NewCat
           ,t1.value
    FROM @table1 AS t1
    OUTER APPLY(SELECT CAST('<x>' + REPLACE(x.value,',','</x><x>') + '</x>' AS XML).value('/x[2]','int')
                FROM @table1 AS x 
                WHERE x.id_t=t1.id_t AND x.id_data=46) AS ID(SecondNr)
    WHERE t1.id_data=43
)
UPDATE UpdateableCTE SET value=NewCat;

SELECT * FROM @table1;