как в t-sql объединить ячейки?
например:
ячейка "Артикул" будет состоять из ячейки "цвета" и ячейки "наименование"
если цвет, например, черний тогда в ячейку "Артикул" идет 1, а, например, наименование "стол" тогда идет 3 и в итоге в ячейке "Артикул" имеем 13
как такое сделать?
Код:
-- создадим примеры для демо
use tempdb;
go
-- допустим есть таблица товаров
create table dbo.MyTable (Name nvarchar(100), Color nvarchar(100));
insert dbo.MyTable values('стол', 'черний');
insert dbo.MyTable values('стул', 'синий');
insert dbo.MyTable values('кровать', 'бэлый-дэцкий');
select * from dbo.MyTable;
go
------------------------------------------------------------------------
-- вариант 1) насчитываем это прямо в запросе
select
Name,
Color,
Art = (
case
when Name = 'стол' then '1'
when Name = 'стул' then '2'
when Name = 'кровать' then '3'
else '0'
end +
case
when Color = 'черний' then '3'
when Color = 'синий' then '2'
when Color = 'бэлый-дэцкий' then '1'
else '0'
end
)
from
dbo.MyTable
;
go
------------------------------------------------------------------------
-- вариант 2) создаем вычисляемый столбец
alter table dbo.MyTable add Art as (
case
when Name = 'стол' then '1'
when Name = 'стул' then '2'
when Name = 'кровать' then '3'
else '0'
end +
case
when Color = 'черний' then '3'
when Color = 'синий' then '2'
when Color = 'бэлый-дэцкий' then '1'
else '0'
end
)
;
go
-- тогда запрос выглядит просто как
select
Name,
Color,
Art
from
dbo.MyTable
;
go
------------------------------------------------------------------------
-- вариант 3) реалистичный. Допустим, товаров много и привязку кода для артикула мы держим в отдельныйх таблицах
create table dbo.MyTableNameArt (Name nvarchar(100) primary key, Art varchar(10));
create table dbo.MyTableColorArt (Color nvarchar(100) primary key, Art varchar(10));
insert dbo.MyTableNameArt select 'стол', '1' union all select 'стул', '2' union all select 'кровать', '3';
insert dbo.MyTableColorArt select 'черний', '3' union all select 'синий', '2' union all select 'бэлый-дэцкий', '1';
--тогда, получить артикул можно запросом:
select
t.Name,
t.Color,
Art = isnull(n.Art,'0') + isnull(c.Art,'0')
from
dbo.MyTable t
left join dbo.MyTableNameArt n on t.Name = n.Name
left join dbo.MyTableColorArt c on t.Color = c.Color
;
go
------------------------------------------------------------------------
-- вариант 3.1) inline-табличная функция. То же самое, только можно убрать это в табличную функцию
-- требуется сервер выше 2000 и работать будет медленнее, чем предыдущий вариант
create function dbo.utf_GetArt(@Name nvarchar(100), @Color nvarchar(100))
returns table as
return (
with n as (
select Art from dbo.MyTableNameArt n where @Name = n.Name
),
c as (
select Art from dbo.MyTableColorArt c where @Color = c.Color
)
select Art = isnull(n.Art,'0') + isnull(c.Art,'0') from n cross join c
)
go
-- тогда сам запрос выглядит
select
t.Name,
t.Color,
a.Art
from
dbo.MyTable t
outer apply dbo.utf_GetArt(t.Name,t.Color) a
;
go
------------------------------------------------------------------------
-- вариант 3.2) скалярная функция. Можно сделать скалярную функцию и убрать ее либо в вчисляемую колонку,
-- либо заюзать в запросе. Не рекомендую этот вариант, т.к. он хуже по скорости чем все предыдущие,
-- кроме того, если для одного товара возможно несколько артикулов, то эта функция отработает иначе чем предыдущие варианты,
-- из выгоды - можно убрать в вычисляемую колоку и сделать красивый компактный код
create function dbo.usf_GetArt(@Name nvarchar(100), @Color nvarchar(100))
returns nvarchar(20) begin
declare @Art nvarchar(20);
set @Art = '';
select top(1) @Art = @Art + isnull(Art,'0') from dbo.MyTableNameArt n where @Name = n.Name
select top(1) @Art = @Art + isnull(Art,'0') from dbo.MyTableColorArt c where @Color = c.Color
return @Art;
end;
go
-- тогда запрос будет такой
select
t.Name,
t.Color,
Art = dbo.usf_GetArt(t.Name, t.Color)
from
dbo.MyTable t
go
-- либо можно убрать в вычислямую колонку
alter table dbo.MyTable drop column Art; --удалим предыдущую колонку из примера 2)
alter table dbo.MyTable add Art as dbo.usf_GetArt(Name,Color);
go
--тогда запрос
select
t.Name,
t.Color,
t.Art
from
dbo.MyTable t
go
------------------------------------------------------------------------
-- удалим функции и таблицы
drop table dbo.MyTableNameArt, dbo.MyTableColorArt, dbo.MyTable;
drop function dbo.utf_GetArt;
drop function dbo.usf_GetArt;
use tempdb;
go
-- допустим есть таблица товаров
create table dbo.MyTable (Name nvarchar(100), Color nvarchar(100));
insert dbo.MyTable values('стол', 'черний');
insert dbo.MyTable values('стул', 'синий');
insert dbo.MyTable values('кровать', 'бэлый-дэцкий');
select * from dbo.MyTable;
go
------------------------------------------------------------------------
-- вариант 1) насчитываем это прямо в запросе
select
Name,
Color,
Art = (
case
when Name = 'стол' then '1'
when Name = 'стул' then '2'
when Name = 'кровать' then '3'
else '0'
end +
case
when Color = 'черний' then '3'
when Color = 'синий' then '2'
when Color = 'бэлый-дэцкий' then '1'
else '0'
end
)
from
dbo.MyTable
;
go
------------------------------------------------------------------------
-- вариант 2) создаем вычисляемый столбец
alter table dbo.MyTable add Art as (
case
when Name = 'стол' then '1'
when Name = 'стул' then '2'
when Name = 'кровать' then '3'
else '0'
end +
case
when Color = 'черний' then '3'
when Color = 'синий' then '2'
when Color = 'бэлый-дэцкий' then '1'
else '0'
end
)
;
go
-- тогда запрос выглядит просто как
select
Name,
Color,
Art
from
dbo.MyTable
;
go
------------------------------------------------------------------------
-- вариант 3) реалистичный. Допустим, товаров много и привязку кода для артикула мы держим в отдельныйх таблицах
create table dbo.MyTableNameArt (Name nvarchar(100) primary key, Art varchar(10));
create table dbo.MyTableColorArt (Color nvarchar(100) primary key, Art varchar(10));
insert dbo.MyTableNameArt select 'стол', '1' union all select 'стул', '2' union all select 'кровать', '3';
insert dbo.MyTableColorArt select 'черний', '3' union all select 'синий', '2' union all select 'бэлый-дэцкий', '1';
--тогда, получить артикул можно запросом:
select
t.Name,
t.Color,
Art = isnull(n.Art,'0') + isnull(c.Art,'0')
from
dbo.MyTable t
left join dbo.MyTableNameArt n on t.Name = n.Name
left join dbo.MyTableColorArt c on t.Color = c.Color
;
go
------------------------------------------------------------------------
-- вариант 3.1) inline-табличная функция. То же самое, только можно убрать это в табличную функцию
-- требуется сервер выше 2000 и работать будет медленнее, чем предыдущий вариант
create function dbo.utf_GetArt(@Name nvarchar(100), @Color nvarchar(100))
returns table as
return (
with n as (
select Art from dbo.MyTableNameArt n where @Name = n.Name
),
c as (
select Art from dbo.MyTableColorArt c where @Color = c.Color
)
select Art = isnull(n.Art,'0') + isnull(c.Art,'0') from n cross join c
)
go
-- тогда сам запрос выглядит
select
t.Name,
t.Color,
a.Art
from
dbo.MyTable t
outer apply dbo.utf_GetArt(t.Name,t.Color) a
;
go
------------------------------------------------------------------------
-- вариант 3.2) скалярная функция. Можно сделать скалярную функцию и убрать ее либо в вчисляемую колонку,
-- либо заюзать в запросе. Не рекомендую этот вариант, т.к. он хуже по скорости чем все предыдущие,
-- кроме того, если для одного товара возможно несколько артикулов, то эта функция отработает иначе чем предыдущие варианты,
-- из выгоды - можно убрать в вычисляемую колоку и сделать красивый компактный код
create function dbo.usf_GetArt(@Name nvarchar(100), @Color nvarchar(100))
returns nvarchar(20) begin
declare @Art nvarchar(20);
set @Art = '';
select top(1) @Art = @Art + isnull(Art,'0') from dbo.MyTableNameArt n where @Name = n.Name
select top(1) @Art = @Art + isnull(Art,'0') from dbo.MyTableColorArt c where @Color = c.Color
return @Art;
end;
go
-- тогда запрос будет такой
select
t.Name,
t.Color,
Art = dbo.usf_GetArt(t.Name, t.Color)
from
dbo.MyTable t
go
-- либо можно убрать в вычислямую колонку
alter table dbo.MyTable drop column Art; --удалим предыдущую колонку из примера 2)
alter table dbo.MyTable add Art as dbo.usf_GetArt(Name,Color);
go
--тогда запрос
select
t.Name,
t.Color,
t.Art
from
dbo.MyTable t
go
------------------------------------------------------------------------
-- удалим функции и таблицы
drop table dbo.MyTableNameArt, dbo.MyTableColorArt, dbo.MyTable;
drop function dbo.utf_GetArt;
drop function dbo.usf_GetArt;