-- Создаем таблицы
CREATE TABLE T1 (id INT IDENTITY(1,1),item1 int,item2 int,item3 INT)
CREATE TABLE T2 (id INT IDENTITY(1,1),item_id INT, itype VARCHAR(10) )
-- Наполняем данными
-- Таблица T1
INSERT INTO [dbo].[T1] ([item1],[item2],[item3])VALUES(11,12,13)
INSERT INTO [dbo].[T1] ([item1],[item2],[item3])VALUES(21,22,23)
INSERT INTO [dbo].[T1] ([item1],[item2],[item3])VALUES(31,32,33)
INSERT INTO [dbo].[T1] ([item1],[item2],[item3])VALUES(41,42,43)
INSERT INTO [dbo].[T1] ([item1],[item2],[item3])VALUES(51,52,53)
INSERT INTO [dbo].[T1] ([item1],[item2],[item3])VALUES(11,32,53)
INSERT INTO [dbo].[T1] ([item1],[item2],[item3])VALUES(17,32,53)
-- Таблица T2
INSERT INTO [dbo].[T2]([item_id],[itype]) VALUES(21,'A')
INSERT INTO [dbo].[T2]([item_id],[itype]) VALUES(11,'B')
INSERT INTO [dbo].[T2]([item_id],[itype]) VALUES(13,'B')
INSERT INTO [dbo].[T2]([item_id],[itype]) VALUES(41,'A')
INSERT INTO [dbo].[T2]([item_id],[itype]) VALUES(42,'A')
INSERT INTO [dbo].[T2]([item_id],[itype]) VALUES(43,'A')
INSERT INTO [dbo].[T2]([item_id],[itype]) VALUES(17,'A')
-- Исходный запрос
SELECT * FROM T1 WHERE
T1.item1 IN (SELECT item_id FROM T2 WHERE itype='A') AND
T1.item2 IN (SELECT item_id FROM T2 WHERE itype='A') AND
T1.item3 IN (SELECT item_id FROM T2 WHERE itype='A')
-- Запрос с одним джойном
;WITH CTE_OneSubQuery
AS
(
SELECT DISTINCT
tt1.id, tt1.item1,tt1.item2,tt1.item3
,CASE (COUNT (tt2.item_id) OVER (PARTITION BY tt1.id)) WHEN 3 THEN 1 END AS [kol]
FROM T1 tt1
JOIN t2 tt2 ON tt2.item_id =CASE
WHEN tt2.item_id = tt1.item1 THEN tt1.item1
WHEN tt2.item_id = tt1.item2 THEN tt1.item2
WHEN tt2.item_id = tt1.item3 THEN tt1.item3
END
WHERE tt2.itype = 'A'
)
SELECT id, item1,item2,item3 FROM CTE_OneSubQuery
WHERE kol =1
и почему индекс (value, date) не работает?
В таких случаях рекомендую делать так :)
Не самое кошерное решение - но зато понятно что происходит и минимум возможности для ошибки :)
--пример таблиц
CREATE TABLE uzer1 (id INT, name1 NVARCHAR(20))
CREATE TABLE uzer2 (id INT, name2 NVARCHAR(20))
-- Заполняем данными
-- Таблица [uzer1]
INSERT INTO [dbo].[uzer1]([id],[name1]) VALUES(1,'Вася')
INSERT INTO [dbo].[uzer1]([id],[name1]) VALUES(2,'Петя')
INSERT INTO [dbo].[uzer1]([id],[name1]) VALUES(3,'Гундяев')
-- Таблица [uzer2]
INSERT INTO [dbo].[uzer2]([id],[name2]) VALUES(1,'Вася')
INSERT INTO [dbo].[uzer2]([id],[name2]) VALUES(3,'Кирил')
--Шаг 1
-- Пишем CTE с джойном двух таблиц - Для проверки что именно у нас на что заменится
;WITH cte_Update
as
(SELECT t1.Name1 AS 'Вот это'
, t2.Name2 AS 'апдейтим на это'
FROM [uzer1] t1
JOIN [uzer2] t2 ON t1.id=t2.id)
--Проверяем что у нас проапдетится именно то что нам надо
SELECT * FROM cte_Update
--Шаг 2
-- пишем все тоже самое только вместо селекта Апдейт
;wITH cte_Update
as
(SELECT t1.Name1 AS 'Вот это'
, t2.Name2 AS 'апдейтим на это'
FROM [uzer1] t1
JOIN [uzer2] t2 ON t1.id=t2.id)
--Апдейтим
UPDATE cte_Update
SET [Вот это] =[апдейтим на это]
-- я использую такой способ, мне он кажется более безопасным и быстрым в написании :)
-- Делаем таблички
CREATE TABLE story( id int ,[text] text,author_id int )
CREATE TABLE story_comments( id int,s_id INT,[text] text)
-- Заполнем данными
TRUNCATE TABLE [story]
TRUNCATE TABLE [story_comments]
INSERT INTO [dbo].[story]([id],[text],[author_id])VALUES(1,'Статья 1',1)
INSERT INTO [dbo].[story]([id],[text],[author_id])VALUES(2,'Статья 2',2)
INSERT INTO [dbo].[story_comments]([id],[s_id],[text])VALUES(1,1,'Первый комент Первой статьи')
INSERT INTO [dbo].[story_comments]([id],[s_id],[text])VALUES(2,1,'Второй комент Первой статьи')
INSERT INTO [dbo].[story_comments]([id],[s_id],[text])VALUES(3,1,'Третий комент Первой статьи')
-- Сам запрос
;WITH cte
AS
(
SELECT [text2]=
(
SELECT
--s.id AS 'Story_ID',
s.[text] AS 'Story_Text'
,
(
SELECT ISNULL(
REPLACE(
REPLACE(
REPLACE(
(SELECT [text]=
(SELECT sc.[text]AS 'comment_Text'
FROM [story_comments] sc
WHERE s.id=sc.[s_id]
FOR XML PATH (''))),'</comment_Text><comment_Text>',',')
,'<comment_Text>','['),'</comment_Text>',']')
,'[NULL]')
)
FROM [story] s
FOR XML PATH('')
))
SELECT '['+
REPLACE(
replace (
REPLACE (text2,'<Story_Text>','[')
,'</Story_Text>[',',[')
,'][','],[')+']'
FROM cte
Ответ:
[[Статья 1,[Первый комент Первой статьи,Второй комент Первой статьи,Третий комент Первой статьи],[Статья 2,[NULL]]
-- Создали таблицы
CREATE TABLE counts (count_id INT IDENTITY (1,1) , count_name nVARCHAR(20))
CREATE TABLE operation (operation_id INT IDENTITY (1,1) ,operation_count_id INT, balance MONEY,operation_date DATETIME ,operation_name NVARCHAR(50))
go
-- Очищаем таблицы
TRUNCATE TABLE counts
TRUNCATE TABLE operation
-- Заполняем данным
INSERT INTO [dbo].[counts] ([count_name]) VALUES ('Первый счет')
INSERT INTO [dbo].[counts] ([count_name]) VALUES ('Второй счет')
INSERT INTO [dbo].[counts] ([count_name]) VALUES ('Третий счет')
INSERT INTO [dbo].[operation]([operation_count_id],[balance],[operation_date],[operation_name])VALUES(1,'10.3','01-01-2015','Первая операция по первому счету')
INSERT INTO [dbo].[operation]([operation_count_id],[balance],[operation_date],[operation_name])VALUES(1,'25.5','02-02-2015','Вторая операция по первому счету')
INSERT INTO [dbo].[operation]([operation_count_id],[balance],[operation_date],[operation_name])VALUES(1,'34.4','03-03-2015','Третья операция по первому счету')
INSERT INTO [dbo].[operation]([operation_count_id],[balance],[operation_date],[operation_name])VALUES(2,'11.7','01-01-2015','Первая операция по Второму счету')
INSERT INTO [dbo].[operation]([operation_count_id],[balance],[operation_date],[operation_name])VALUES(2,'22.2','04-04-2015','Вторая операция по Второму счету')
INSERT INTO [dbo].[operation]([operation_count_id],[balance],[operation_date],[operation_name])VALUES(3,'33.1','01-01-2015','Первая операция по Тертья счету')
INSERT INTO [dbo].[operation]([operation_count_id],[balance],[operation_date],[operation_name])VALUES(3,'33.7','02-02-2015','Вторая операция по Третья счету')
-- Запрос возвращает баланс последней операции по каждому счету
SELECT c.count_id,c.count_name
,o2.balance
,o2.operation_name
FROM counts c
JOIN (
SELECT operation_count_id,
MAX(operation_date) AS 'Max Date'
FROM dbo.operation
GROUP BY operation_count_id
) o ON o.operation_count_id=c.count_id
JOIN dbo.operation o2 ON o2.operation_count_id=o.operation_count_id AND o2.operation_date=o.[Max Date]
-- Создали таблицы
CREATE TABLE table1 (Numer INT,Data DATETIME , value1 FLOAT,value2 FLOAT)
CREATE TABLE table2 (Numer INT,Data DATETIME , value1 FLOAT,value2 FLOAT)
go
-- Очищаем таблицы
TRUNCATE TABLE table1
TRUNCATE TABLE table2
-- Заполняем данным
INSERT INTO dbo.table1 ( Numer, Data, value1, value2 ) VALUES ( 1, '01.01.2015', 1.1, 1.2 ) -- только в первой таблице
INSERT INTO dbo.table1 ( Numer, Data, value1, value2 ) VALUES ( 1, '01.01.2015', 1.2, 1.2 )
INSERT INTO dbo.table1 ( Numer, Data, value1, value2 ) VALUES ( 2, '01.01.2014', 2.1, 2.2 )
INSERT INTO dbo.table1 ( Numer, Data, value1, value2 ) VALUES ( 5, '01.01.2014', 3.1, 1.2 )
INSERT INTO dbo.table1 ( Numer, Data, value1, value2 ) VALUES ( 4, '01.01.2015', 1.1, 4.2 )
-- Заполняем данным
INSERT INTO dbo.table2 ( Numer, Data, value1, value2 ) VALUES ( 1, '01.01.2015', 1.2, 1.2 )
INSERT INTO dbo.table2 ( Numer, Data, value1, value2 ) VALUES ( 2, '01.01.2014', 2.1, 2.2 )
INSERT INTO dbo.table2 ( Numer, Data, value1, value2 ) VALUES ( 3, '01.01.2014', 5.1, 1.2 ) -- Искажение в первом значении
INSERT INTO dbo.table2 ( Numer, Data, value1, value2 ) VALUES ( 4, '01.01.2015', 1.1, 4.3 ) -- Искажение в втором значении
go
SELECT 'Нет совпадения по номеру и дате'
,
* FROM dbo.table1 t1
FULL JOIN dbo.table2 t2
ON t2.Data = t1.Data AND t2.Numer = t1.Numer
WHERE t2.Numer IS NULL OR t1. Numer IS NULL
UNION ALL
SELECT 'Нет совпадения по первому значению'
, * FROM dbo.table1 t1
JOIN dbo.table2 t2
ON t2.Data = t1.Data AND t2.Numer = t1.Numer
AND t2.value2 = t1.value2
where t2.value1 <> t1.value1
UNION ALL
SELECT 'Нет совпадения по второму значению'
, * FROM dbo.table1 t1
JOIN dbo.table2 t2
ON t2.Data = t1.Data AND t2.Numer = t1.Numer
AND t2.value1 = t1.value1
where t2.value2 <> t1.value2