IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

MS SQL Server Discussion :

ma fonction m'affiche Null


Sujet :

MS SQL Server

  1. #1
    Nouveau candidat au Club
    Inscrit en
    Décembre 2008
    Messages
    1
    Détails du profil
    Informations forums :
    Inscription : Décembre 2008
    Messages : 1
    Par défaut ma fonction m'affiche Null
    après avoir créé ma fonction puis la teste, elle m'affiche null dans le cas ou il y une valeur égale à 0

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    create FUNCTION dbo.fnmoyanparmat
    (@moy1 as float , @moy2 as float)
    returns float
     begin
    declare @result float
    if @moy1>0 and @moy2>0 
    set @result=(@moy1*1+@moy2*2)/3
    return @result
    if @moy1=0  and @moy2>0
    set @moy1=0
    set @result=@moy2
    return @result
    if @moy1>0 and @moy2=0 
    set @moy2=0
    set @result=@moy1
    return @result
    end;
     
    GO
    select dbo.fnmoyanparmat((12),0)

  2. #2
    Membre Expert

    Homme Profil pro
    Ingénieur développement logiciels
    Inscrit en
    Septembre 2003
    Messages
    733
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Haute Garonne (Midi Pyrénées)

    Informations professionnelles :
    Activité : Ingénieur développement logiciels
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Septembre 2003
    Messages : 733
    Billets dans le blog
    8
    Par défaut
    Ton problème vient d'u fait qu’il te manque des BEGIN et des END !!! (voir ci-dessous).
    Code SQL : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    create FUNCTION dbo.fnmoyanparmat
    (@moy1 as float , @moy2 as float)
    returns float
    begin
    declare @result float
    if @moy1>0 and @moy2>0 
    set @result=(@moy1*1+@moy2*2)/3
    return @result  -- Ton problème vient d'Ici ! il te manque des BEGIN et des END   !!!! 
                    -- En effet, le programme passe toujours par Ici alors que la variable @result n'est toujours initialisée  !!! 
    if @moy1=0 and @moy2>0
    set @moy1=0
    set @result=@moy2
    return @result
    if @moy1>0 and @moy2=0 
    set @moy2=0
    set @result=@moy1
    return @result
    end;
    Tu devrais au moins procéder comme ceci :
    Code SQL : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
    create FUNCTION dbo.fnmoyanparmat
    (@moy1 as float , 
     @moy2 as float)
    returns float
    begin
    declare @result float
    if @moy1>0 and @moy2>0 
     begin 
       set @result=(@moy1*1+@moy2*2)/3
       return @result
     end
    if @moy1=0 and @moy2>0
      begin 
    	set @moy1=0 -- instruction inutile !!! 
    	set @result=@moy2
    	return @result
      end; 
    if @moy1>0 and @moy2=0 
      begin   
    	set @moy2=0    -- Instruction inutile !!! 
    	set @result=@moy1
    	return @result
      end; 
      Return @Result;  
    end;
    Evites, si possible, dans le corps d’une fonction, de faire des ‘RETURN à divers endroits ! même si sur le plan syntaxique c’est correcte, Cela nuit à la lisibilité du code. Tu pourras simplifier et rendre ainsi plus lisible ton code en le transformant comme suit :
    Code SQL : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    CREATE FUNCTION dbo.fnmoyanparmat
    (@moy1 AS FLOAT , 
     @moy2 AS FLOAT)
    RETURNS FLOAT
    BEGIN
    DECLARE @result FLOAT
    IF @moy1 > 0 AND @moy2 > 0 
      SET @result = (@moy1*1 + @moy2*2)/3
    ELSE IF ISNULL(@moy1,0) = 0 AND @moy2 > 0
      SET @result = @moy2
    ELSE IF @moy1 > 0 and ISNULL(@moy2,0) = 0 
      SET @result = @moy1
    ELSE 
      SET @result = 0; 
    RETURN @result; 
    END;

    Code SQL : Sélectionner tout - Visualiser dans une fenêtre à part
    select dbo.fnmoyanparmat((12),0)
    Résultat :
    A+

  3. #3
    Modérateur

    Homme Profil pro
    Administrateur de base de données
    Inscrit en
    Janvier 2005
    Messages
    5 826
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 44
    Localisation : France, Haute Garonne (Midi Pyrénées)

    Informations professionnelles :
    Activité : Administrateur de base de données
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Janvier 2005
    Messages : 5 826
    Par défaut
    Bonjour,

    Boudiou que c'est compliqué tout ça ! Il faudrait se mettre un peu au SQL, avec un CASE tout simple :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    CREATE FUNCTION dbo.fnmoyanparmat
    	(
    		@moy1 float
    		, @moy2 float
    	)
    RETURNS float
    WITH SCHEMABINDING
    AS
    BEGIN
    	RETURN
    	(
    		CASE
    			WHEN @moy1 > 0 AND @moy2 > 0 THEN (@moy1 + @moy2 * 2) / 3
    			WHEN @moy1 = 0 AND @moy2 > 0 THEN @moy2
    			WHEN @moy1 > 0 AND @moy2 = 0 THEN @moy1
    		END
    	)
    END
    Cela étant, il semble que ce soit la saison des fonctions scalaires : beaucoup de participants posent des questions sur ce type de fonctions, mais comme je l'ai démontré ici, elles sont contre-performantes.

    Il est si simple de transformer cette fonction en une fonction de table incluse :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    CREATE FUNCTION dbo.fnmoyanparmat
    	(
    		@moy1 float
    		, @moy2 float
    	)
    RETURNS TABLE
    WITH SCHEMABINDING
    AS
    	RETURN
    	(
    		SELECT CASE
    			WHEN @moy1 > 0 AND @moy2 > 0 THEN (@moy1 + @moy2 * 2) / 3
    			WHEN @moy1 = 0 AND @moy2 > 0 THEN @moy2
    			WHEN @moy1 > 0 AND @moy2 = 0 THEN @moy1
    		END AS moy
    	)
    L'utilisation en combinaison avec CROSS APPLY (disponible dès SQL Server 2005) est alors enfantine :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    DECLARE @t TABLE
    (
    	i float
    	, j float
    )
     
    INSERT	INTO @t
    SELECT ABS(CHECKSUM(NEWID())) % 10, ABS(CHECKSUM(NEWID())) % 10
    UNION ALL SELECT ABS(CHECKSUM(NEWID())) % 10, ABS(CHECKSUM(NEWID())) % 10
    UNION ALL SELECT ABS(CHECKSUM(NEWID())) % 10, ABS(CHECKSUM(NEWID())) % 10
    UNION ALL SELECT ABS(CHECKSUM(NEWID())) % 10, ABS(CHECKSUM(NEWID())) % 10
    UNION ALL SELECT ABS(CHECKSUM(NEWID())) % 10, ABS(CHECKSUM(NEWID())) % 10
    UNION ALL SELECT ABS(CHECKSUM(NEWID())) % 10, ABS(CHECKSUM(NEWID())) % 10
    UNION ALL SELECT ABS(CHECKSUM(NEWID())) % 10, ABS(CHECKSUM(NEWID())) % 10
     
    SELECT	*
    FROM	@t
     
    SELECT		T.i
    		, T.j
    		, MAP.moy
    FROM		@t AS T
    CROSS APPLY	dbo.fnmoyanparmat(T.i, T.j) AS MAP
    @++

Discussions similaires

  1. Réponses: 5
    Dernier message: 13/06/2007, 15h05
  2. Ma fonction qui affiche les mois débloque
    Par isa150183 dans le forum Langage
    Réponses: 4
    Dernier message: 19/10/2006, 20h05
  3. Fonction "is not null" ?
    Par Phenomenium dans le forum ASP
    Réponses: 2
    Dernier message: 03/10/2006, 12h09
  4. ça affiche NULL mais je veux que ça affiche rien.
    Par psychoBob dans le forum Général JavaScript
    Réponses: 11
    Dernier message: 20/05/2006, 22h35
  5. Réponses: 9
    Dernier message: 17/02/2006, 11h04

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo