我正在尝试编写一个SQL语句,其中包含一些级联条件逻辑。我有几个需要返回的字段,但它们的值是以先前确定的字段为条件的。例如,buysell_flag取决于spotfwd_flag值,counter_amt和given_amt取决于buysell_flag值,依此类推。
我很快发现我无法在同一个空间中组合数据检索查询和变量分配查询,所以我尝试了各种各样的东西,但无法返回我想要的数据。这是客户端的模板,客户端将编辑此SQL并将其粘贴到程序中。它并不总是相同的,所以我无法处理程序或存储过程或UDF中的逻辑。我试图使用一个表,但是当插入它并选择它的东西时,我遇到了同样的问题。您可以在下方看到我的尝试,但如果无法完成,请告诉我 - 否则,我愿意接受任何建议!谢谢!
DECLARE @trans_type nvarchar(255), @trade_date nvarchar(255), @settle_date nvarchar(255),
@order_id nvarchar(255), @oaexecbroker nvarchar(255), @exec_broker nvarchar(255),
@ostatus nvarchar(255), @trade_id nvarchar(255), @reference_price nvarchar(255),
@given_ccy nvarchar(255), @spotfwd_flag nvarchar(255), @buysell_flag nvarchar(255),
@counter_ccy nvarchar(255), @counter_amt nvarchar(255), @given_amt nvarchar(255),
@oacct_cd nvarchar(255)
SELECT
@trans_type = o.trans_type,
@settle_date = o.settle_date,
@order_id = o.order_id,
@oaexecbroker = oa.exec_broker,
@exec_broker = o.exec_broker,
@ostatus = o.status,
@trade_id = oa.trade_id,
@reference_price = o.exec_price,
@given_ccy = o.target_crrncy,
--o.trans_type AS trans_type,
-- o.trade_date AS trade_date,
-- o.settle_date AS settle_date,
-- o.order_id AS order_id,
-- oa.exec_broker AS oaexecbroker,
-- o.exec_broker AS exec_broker,
-- o.status AS ostatus,
-- oa.trade_id AS trade_id,
-- o.exec_price AS reference_price,
-- o.target_crrncy as given_ccy,
-- for spot/fwd
@spotfwd_flag = CASE
WHEN LEFT(o.inv_class_cd,1) = 'F' THEN ('FWD')
WHEN LEFT(o.inv_class_cd,2) = 'CU' THEN ('SPOT')
ELSE 'SPOT'
END, -- must be spot or fwd
--for buysell
@buysell_flag = CASE
WHEN @spotfwd_flag = 'FWD' THEN
CASE
WHEN o.target_crrncy = o.to_crrncy THEN 'BUY'
ELSE 'SELL'
END
ELSE
CASE
WHEN o.trans_type = 'BUYL' THEN 'BUY'
ELSE 'SELL'
END
END, -- must be buy or sell
@counter_amt = CASE
WHEN @buysell_flag = 'BUY' Then oa.exec_amt
ELSE oa.exec_qty
END,
@given_amt = CASE
WHEN @buysell_flag = 'SELL' THEN oa.exec_amt
ELSE oa.exec_qty
END,
@counter_ccy = CASE
WHEN o.target_crrncy = o.to_crrncy THEN o.from_crrncy
ELSE o.to_crrncy
END,
@oacct_cd = CASE
WHEN f.udf_char6 = 'Y' THEN (oa.acct_cd + oa.custodian)
ELSE oa.acct_cd
END
FROM ts_order_alloc oa
LEFT OUTER JOIN ts_order o
ON oa.order_id = o.order_id
LEFT OUTER JOIN cs_fund f
ON oa.acct_cd = f.acct_cd
-- LEFT OUTER JOIN csm_security s
-- ON o.sec_id = s.sec_id
--WHERE s.sec_typ_cd IN ( 'CFWD', 'CURR' )
-- AND o.status IN ( 'READY','ACCT' )
-- AND oa.usr_class_cd_2 = 'GTSSREADY'
select @trans_type as trans_type,
@trade_date AS trade_date,
@settle_date AS settle_date,
@order_id AS order_id,
@oaexecbroker AS oaexecbroker,
@exec_broker AS exec_broker,
@ostatus AS ostatus,
@trade_id AS trade_id,
@reference_price AS reference_price,
@given_ccy as given_ccy,
@buysell_flag as buysell_flag,
@spotfwd_flag as spotfwd_flag,
@given_ccy as given_ccy,
@counter_ccy as counter_ccy,
@given_amt as given_amt,
@counter_amt as counter_amt
编辑:
我希望根据给定的变量获取行。我有这么多变量的原因是我试图让它符合SQL错误消息。
应该这样出来:
trans_type trade_date settle_date order_id oaexecbroker exec_broker ostatus trade_id reference_price given_ccy buysell_flag spotfwd_flag given_ccy counter_ccy given_amt counter_amt
BUYL NULL 2010-04-06 00:00:00.000 1442084139 3PCITI 3PCITI Ready 1389278710 1.50705 GBP BUY SPOT GBP USD 604292 910699
答案 0 :(得分:0)
如果我正确理解了这个问题,你需要做的是封装计算的逻辑,以便稍后使用这些计算的结果。
根据计算的输入,有很多不同的方法可以做到这一点。
如果逻辑仅涉及单个表中单个行中的值,则可以定义computed column来封装逻辑。这是如何工作的当你SELECT
计算列的值时,计算是自动完成的。当您需要非常频繁地重用相同的逻辑时,此方法是合适的,因为这是对表结构的永久性更改。
封装逻辑的一种好方法是在视图中。这有点像持久列,除了结果可以组合来自多个表的数据。由于视图只能包含单个SELECT
语句,因此您可以将其与此处提供的任何其他方法结合使用。
派生表格。这看起来很奇特,但概念非常简单:使用SELECT
语句的结果作为另一个SELECT
语句的输入。请看以下示例:
DECLARE @test table
(
Col1 int,
Col2 int
);
-- Result query (2)
SELECT
a.Col1,
(
CASE
WHEN a.Col3 < a.Col1 THEN 1 -- Use the computation
ELSE 5
END
) AS Col4
FROM
(
-- Derived table (1)
SELECT
Col1,
Col2 + Col1 AS Col3 -- Compute
FROM @test t1
) a;
最内层查询首先发生(1),而在外部查询(2)中,您可以使用内部查询的结果。继续嵌套,直到计算中没有“层”为止。
公用表表达式(CTE)。这与派生表类似,但语法稍有不同,它们使您能够在主查询中多次重用逻辑。从本质上讲,CTE就像一个只存在于单个查询中的视图。以下是与上面相同的示例,使用CTE而不是派生表:
DECLARE @test table
(
Col1 int,
Col2 int
);
WITH a AS
(
-- CTE (1)
SELECT
Col1,
Col2 + Col1 AS Col3 -- Compute
FROM @test t1
)
-- Result query (2)
SELECT
a.Col1,
(
CASE
WHEN a.Col3 < a.Col1 THEN 1 -- Use the computation
ELSE 5
END
) AS Col4
FROM a;
对于您发布的查询,您需要超过2个图层,因此您可能需要组合这些方法中的一些,或者仅使用派生表来处理所有内容。最重要的是,应用这些方法后,您可能会发现不需要使用任何标量变量!