Результаты присоединения sql 2005 - PullRequest
0 голосов
/ 11 ноября 2009

HI

Использование Microsoft SQL Server 2005:

У меня есть таблица "тест":

id, link_id, name

1 11 test1

2 11 test2

3 11 test3

4 12 test4

Есть ли способ сделать запрос и вернуть результаты, сгруппированные по "link_id", с присоединенными именами?

EG,

ВЫБРАТЬ link_id, имя ОТ теста, ГДЕ ???????

Результаты:

link_id, имя (имена)

11 test1, test2, test3

12 test4

Ответы [ 8 ]

5 голосов
/ 11 ноября 2009

Черный ящик может сделать это с помощью CROSS APPLY и FOR XML PATH:

declare @t table (id int, link_id int, name varchar(max))
insert into @t select 1, 11, 'test1'
union all select 2, 11, 'test2'
union all select 3, 11, 'test3'
union all select 4, 12, 'test4'

select b.link_id, d.link_names
from (
    select distinct link_id
    from @t a
) b
cross apply (
    select name + ', ' as [text()]
    from @t c
    where b.link_id = c.link_id
    for xml path('')
) d (link_names)

Для каждой строки CROSS APPLY выполняет примененный подзапрос. В этом случае подзапрос вызывается дважды, для link_id 11 и 12. Затем подзапрос использует оператор FOR XML для добавления строк вместе.

Если вы запустите запрос, он напечатает:

11   test1, test2, test3, 
12   test4, 
2 голосов
/ 11 ноября 2009

Пример рекурсивного CTE:

declare @t table (id int
                , link_id int
                , [name] varchar(10) )


insert @t
      select 1,11,'test1'
union select 2,11,'test2'
union select 3,11,'test3'
union select 4,12,'test4'

;with rnCTE
AS
(
        select * 
               ,ROW_NUMBER() OVER (PARTITION BY link_id
                                   ORDER BY  id
                                   ) AS rn
               ,ROW_NUMBER() OVER (PARTITION BY link_id
                                   ORDER BY  id desc
                                   ) AS rd
        from @t
)
,recCTE
AS
(       select link_id
               ,cast([name] as varchar(max)) as [name]
               ,rn
               ,rd
        from rnCTE
        where rn = 1

        UNION ALL

        select c.link_id
               ,c.[name] + ', ' + t.name as [name]
               ,t.rn
               ,t.rd
        from recCTE c
        join rnCTE  t
        on   t.link_id = c.link_id
        and  t.rn      = c.rn + 1
)
select * from recCTE 
where rd = 1 
order by link_id
0 голосов
/ 13 ноября 2009

Хорошая статья, которая описывает различные подходы

* ** 1003 тысячи два *http://www.simple -talk.com / SQL / T-SQL-программирование / конкатенация-строка-значения-в-Transact-SQL /
0 голосов
/ 11 ноября 2009

Сначала создайте функцию.

Create FUNCTION [dbo].[getname]

( - Добавить параметры для функции здесь @link_ID как int ) ВОЗВРАЩАЕТСЯ varchar (1000) КАК НАЧАТЬ - Объявите возвращаемую переменную здесь ОБЪЯВИТЬ @names как varchar (1000)

-- Add the T-SQL statements to compute the return value here
SELECT @names = Coalesce(@names + ',', '') + Convert(varchar(1000), name)
from tblTableName
where link_ID = @link_ID

-- Return the result of the function
RETURN @names

END

тогда

select link_ID, GetName(link_ID) from tblOctHotelImages group by Link_ID, GetName(link_ID)

Вы получите результат.

0 голосов
/ 11 ноября 2009

Попробуйте синтаксис PIVOT?

http://msdn.microsoft.com/en-us/library/ms177410.aspx

0 голосов
/ 11 ноября 2009

В чистом SQL лучше всего написать функцию скалярного значения, которая сгруппировала бы все ваши имена, например:

DECLARE @Names TABLE (id INT IDENTITY NOT NULL, name NVARCHAR(255))
INSERT INTO @Names SELECT name FROM test WHERE link_id = @link_id

DECLARE @ConcatString NVARCHAR(MAX)

WHILE EXISTS(SELECT NULL FROM @Names)
BEGIN
  SELECT @ConcatString = @ConcatString + ', ' + (SELECT TOP 1 name FROM @Names)
  DELETE FROM @Names WHERE id = (SELECT TOP 1 id FROM @Names)
END

RETURN @ConcatString

Тогда вы можете просто сделать:

SELECT link_id, dbo.FunctionName(link_id)
FROM test
GROUP BY link_id
0 голосов
/ 11 ноября 2009

Вы можете использовать CTE (Common Table Expressions) для достижения этого на уровне базы данных. Поначалу с ними немного сложно работать, но их можно использовать для решения некоторых интересных проблем. MSDN Link

0 голосов
/ 11 ноября 2009

Взгляните на эту статью

http://www.sqlprof.com/blogs/sqldev/archive/2008/03/31/how-to-list-multiple-rows-of-data-on-same-line.aspx

В основном вам нужно создать функцию, которая будет возвращать часть test1, test2, test3. Это делается путем установки переменной. Объедините это с четким списком link_id, и вы получите результат.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...