2010-11-25 5 views
0

utilisant SQLServer 2008.table à langer multi-instruction fonction de valeur (TVF) à inline TVF

Exemple TVF multi-instruction:

CREATE TABLE DBO.DECTEST (ID INT NOT NULL PRIMARY KEY, 
V1 DECIMAL(18,6) NOT NULL, V2 DECIMAL(18,6) NOT NULL) 

INSERT DECTEST VALUES (1, 23.1234, 25.22) 

GO 

DROP FUNCTION DBO.F_DECTEST1 
GO 
CREATE FUNCTION DBO.F_DECTEST1 
(
@ID INT 
) 
RETURNS @RESULT TABLE 
( 
    V1 DECIMAL(18,6), 
    V2 DECIMAL(18,6) 
) 
AS 
BEGIN 
    DECLARE @V1 DECIMAL (18,6) 
    DECLARE @V2 DECIMAL(18,6) 
    SELECT @V1 = V1, @V2 = V2 FROM DBO.DECTEST WHERE ID = @ID 

    INSERT @RESULT (V1, V2) VALUES (ISNULL(@V1, 0), ISNULL(@V2, 0)) 
    RETURN 
END 
GO 

Je veux changer cela à un TVF en ligne (pour des raisons de performance). Notez qu'une ligne est toujours renvoyée dans le jeu de résultats - même si un ID inexistant est passé. Existe-t-il un moyen propre de faire cela?

Répondre

1

Ne pas savoir si cela est mieux, mais vous pouvez essayer ce ...

CREATE FUNCTION DBO.F_DECTEST1 
( 
@ID INT 
) 
RETURNS TABLE 
AS 
RETURN 
(
    SELECT V1, V2 FROM DBO.DECTEST WHERE ID = @ID 
    UNION ALL 
    SELECT NULL AS V1, NULL AS V2 WHERE NOT EXISTS (SELECT 1 FROM DBO.DECTEST WHERE ID = @ID) 
) 

Aussi, pourquoi ne pas aller avec un proc stockée avec des paramètres de sortie? Puisque l'ID est unique et que vous devez retourner une seule ligne.

+0

nous voulez un TVF afin que nous puissions utiliser CROSS APPLY avec. J'avais peur que la version inline soit plutôt moche, mais merci d'avoir essayé. –

0

Pour ceux qui sont encore intéressés, c'est ce que je cherchais (Notez que j'aurais vraiment fait colonnes V1 et V2-able NULL dans mon exemple d'origine afin de mieux refléter ce que je cherchais):

CREATE FUNCTION DBO.F_DECTEST1 
(
@ID INT 
) 
RETURNS TABLE 
AS 
RETURN 
(
    SELECT ISNULL(w.V1, 0) AS V1 , ISNULL(w.V2, 0) AS V2 
    FROM 
    (SELECT @ID AS ID) s 
    OUTER APPLY 
    (
     SELECT V1, V2 FROM DBO.DECTEST WHERE ID = s.ID 
    ) w 
)