web-dev-qa-db-ja.com

異なるテーブルの列に基づく計算列の式

次の表を検討してください:c_const

 code  |  nvalue
 --------------
 1     |  10000
 2     |  20000  

および別のテーブルt_anytable

 rec_id |  s_id  | n_code
 ---------------------
 2      |  x     | 1

目標は、s_idは、次の式に基づいた計算列です。

 rec_id*(select nvalue from c_const where code=ncode)

これによりエラーが発生します。

このコンテキストでは、サブクエリは許可されていません。スカラー式のみが許可されます。

別のテーブルの列を入力として使用して、この計算列の値を計算するにはどうすればよいですか?

46

このためのユーザー定義関数を作成できます。

CREATE FUNCTION dbo.GetValue(@ncode INT, @recid INT)
RETURNS INT
AS 
   SELECT @recid * nvalue 
   FROM c_const 
   WHERE code = @ncode

次に、それを使用して計算列を定義します。

ALTER TABLE dbo.YourTable
   ADD NewColumnName AS dbo.GetValue(ncodeValue, recIdValue)
71
marc_s

これは、ビュー(計算列の高速ルックアップが必要な場合はインデックス付きビュー)の仕事のようです。

CREATE VIEW AnyView
WITH SCHEMABINDING
AS

SELECT a.rec_id, a.s_id, a.n_code, a.rec_id * c.nvalue AS foo
FROM AnyTable a
INNER JOIN C_Const c
    ON c.code = a.n_code

これは、結合の結果が複数ある場合にエラーを生成する代わりに複数のレコードを返すという点で、サブクエリバージョンとはわずかに異なります。しかし、それはc_const.codeUNIQUE制約で簡単に解決できます(すでにPRIMARY KEYであると思われます)。

また、誰かがサブクエリバージョンよりも理解するのがはるかに簡単です。

Marc_sが示したように、サブクエリとUDFでそれを行うことができますが、スカラーUDFを計算する必要があるため、単純なJOINと比較して非効率である可能性があります-行ごと。

24
Aaronaught