我正在尝试运行以下查询:
create table MyTable (
TableIndex bigint primary key identity(1,1) not null,
ForeignKey1 int not null,
ForeignKey2 char(16) not null,
fldSomeNumber float(24),
fldScore as cast(case
when fldSomeNumber is null or fldCSIPercentage=0 then 0
when fldSomeNumber <= 0.09 then (select fldTenthScore from tblScores where ScorePrimaryKey=MyTable.ForeignKey2)
when fldSomeNumber <= 0.9 then (select fld1Score from tblScores where ScorePrimaryKey=MyTable.ForeignKey2)
...
else 100 end as float(24))
);
但是我一直收到以下错误:“在此上下文中不允许使用子查询。只允许使用标量表达式。”是否不可能将子选择放在这样的计算列中?
我正在运行SQL Server Express 2016。
答案 0 :(得分:1)
你不能真正用一个表做你想要的东西,你会想要使用一个视图并将计算列放在视图上。
所以看起来像这样的视图
CREATE VIEW MyView AS
SELECT
cast(case
when fldSomeNumber is null or fldCSIPercentage=0 then 0
when fldSomeNumber <= 0.09 then tblScores.fldTenthScore
when fldSomeNumber <= 0.9 then tblScores.fld1Score
...
else 100 end as float(24)) AS fldScore
FROM
MyTable
INNER JOIN tblScores
ON tblScores.ScorePrimaryKey = MyTable.ForeignKey2
请参阅此问题的第二个答案:
formula for computed column based on different table's column
答案 1 :(得分:0)
使用CREATE TABLE
时,必须分别使用列名和数据类型,但是当您编写fldScore
列名时,会插入值而不是数据类型。因为CASE
结构返回一个值,并且您只将此值作为浮点数转换。
但是,如果您的意思是计算列,则只能使用当前表中的列来定义不是来自其他表的计算列。
答案 2 :(得分:0)
使用函数解决此问题的方法(如mallan1121所推荐)如下:
IF EXISTS (
SELECT * FROM sysobjects WHERE id = object_id('fnCalculateScore')
AND xtype IN ('FN', 'IF', 'TF')
)
DROP FUNCTION fnCalculateScore
go
create function fnCalculateScore (
@SomeNumber float(24),
@SomeKey char(16)
)
returns float(24)
with schemabinding
as
begin
return (select case
when @SomeNumber is null or @SomeNumber=0 then 0
when @SomeNumber <= 0.09 then (select fldTenthScore from dbo.tblScores where ScorePrimaryKey=@SomeKey)
when @SomeNumber <= 0.9 then (select fld1Score from dbo.tblScores where ScorePrimaryKey=@SomeKey)
...
else 100 end as float(24))
end
go
create table MyTable (
TableIndex bigint primary key identity(1,1) not null,
ForeignKey1 int not null,
ForeignKey2 char(16) not null,
fldSomeNumber float(24),
fldScore as dbo.fnCalculateScore(fldSomeNumber, ForeignKey2)
);