我们在Sql Server 2005上有两个相关的表(inventory和inventoryLocalization)。 第一个表的脚本。
CREATE TABLE [dbo].[inventory](
[code] [varchar](35) NOT NULL,
[salePrice1] [decimal](22, 2) NULL,
CONSTRAINT [PK_inventory] PRIMARY KEY CLUSTERED
(
[code] ASC
)WITH (PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF, IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS = ON, ALLOW_PAGE_LOCKS = ON) ON [PRIMARY]
) ON [PRIMARY]
,第二个是;
CREATE TABLE [dbo].[inventoryLocalization](
[code] [varchar](35) NOT NULL,
[language] [varchar](2) NOT NULL,
[name] [nvarchar](100) NOT NULL,
[description] [nvarchar](max) NULL,
CONSTRAINT [PK_inventoryLocalization] PRIMARY KEY CLUSTERED
(
[code] ASC,
[language] ASC,
[name] ASC
)WITH (PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF, IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS = ON, ALLOW_PAGE_LOCKS = ON) ON [PRIMARY]
) ON [PRIMARY]
我们有一个查询取决于这两个,如下:
select i.[code],
iL.[language],
case
when iL.[name] is null then (select iL2.name from dbo.inventoryLocalization iL2 where iL2.[language] = 'de' and iL2.code = i.[code])
else iL.[name]
end as [name]
from dbo.inventory i
left join dbo.inventoryLocalization iL on i.code = iL.code and iL.[language] = 'en';
正如您猜测的那样,我们选择[language] ='en'的所有记录,但如果没有'en'记录,则查询采用'de'(默认)。 但该查询需要更长的时间(大约13秒)。
你认为任何其他优雅的方法可以减少相同的结果吗?
提前感谢您提供的任何帮助。
答案 0 :(得分:4)
可能很慢,因为当case语句评估null并运行子查询时,它必须按需执行查询。
也许这会更快,总是连接到'de',而不是每次找到null时都进行查询。
select i.[code],
iL.[language],
case
when iL.[name] is null then iL2.name
else iL.[name]
end as [name]
from dbo.inventory i
left join dbo.inventoryLocalization iL on i.code = iL.code and iL.[language] = 'en'
left join dbo.inventoryLocalization iL2 on i.code = iL2.[code] and iL2.[language] = 'de'
答案 1 :(得分:2)
select i.code
,coalesce(en.language, de.language) as language
,coalesce(en.name, de.name) as name
from inventory i
left join inventoryLocalization en on(i.code = en.code and en.language = 'en')
left join inventoryLocalization de on(i.code = de.code and de.language = 'de');
答案 2 :(得分:0)
试试这个:
select i.[code],
iL.[language],
coalesce(il.[name],il2.[name],'Unknown') as [name]
from dbo.inventory i
left join dbo.inventoryLocalization iL on i.code = iL.code and iL.[language] = 'en';
left join dbo.inventoryLocalization iL2 on i.code=il2.code and il2.[language] = 'de'