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

SQL Procédural MySQL Discussion :

condition dans une fonction SQL


Sujet :

SQL Procédural MySQL

  1. #1
    Membre actif Avatar de schwarzy2
    Femme Profil pro
    Développeur Web
    Inscrit en
    Septembre 2006
    Messages
    464
    Détails du profil
    Informations personnelles :
    Sexe : Femme
    Âge : 37
    Localisation : France

    Informations professionnelles :
    Activité : Développeur Web
    Secteur : High Tech - Multimédia et Internet

    Informations forums :
    Inscription : Septembre 2006
    Messages : 464
    Points : 288
    Points
    288
    Par défaut condition dans une fonction SQL
    Bonjour à tous,

    J'utilise aujourd'hui deux fonctions pour calculer l'âge d'une personne, soit je calcule l'âge par rapport à la date du jour, et alors je n'ai besoin que d'un paramètre(la date de naissance), soit je calcule l'âge par rapport à une date que je passe en paramètre j'ai alors deux paramètres.
    J'ai donc :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
     
    CREATE FUNCTION age( naissanceamj INT) RETURNS INT 
    RETURN (
    SELECT SUBSTRING(CURDATE()-naissanceamj,1,length(curdate()-naissanceamj)-4)
    ) ;
     
    CREATE FUNCTION `age_d`( naissanceamj INT,date INT) RETURNS int(11)
    RETURN (
    SELECT SUBSTRING(date-naissanceamj,1,length(date-naissanceamj)-4)
    )
    Mais je voudrais de pas avoir à vérifier en PHP si j'ai ma date ou non pour décider ensuite de quel fonction utiliser, j'aimerais faire dans ma fonction SQL un
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    IF date='' THEN SELECT SUBSTRING(CURDATE()-naissanceamj,1,length(curdate()-naissanceamj)-4)
    ELSE SELECT SUBSTRING(date-naissanceamj,1,length(date-naissanceamj)-4)
    END IF
    mais cette syntaxe ne fonctionne pas.
    Pas plus que celle-ci:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    SELECT IF(date=’’,SUBSTRING(CURDATE()-naissanceamj,1,length(curdate()-naissanceamj)-4), SUBSTRING(date-naissanceamj,1,length(date-naissanceamj)-4))
    A l'utilisation j'ai le message d'erreur suivant:
    #1054 - Unknown column '’’' in 'field list'

    Si quelqu'un voulait bien m'aider?
    merci d'avance
    Feel good, feel geek

  2. #2
    Rédacteur/Modérateur

    Avatar de Antoun
    Homme Profil pro
    Architecte décisionnel
    Inscrit en
    Octobre 2006
    Messages
    6 284
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 54
    Localisation : France, Paris (Île de France)

    Informations professionnelles :
    Activité : Architecte décisionnel
    Secteur : Conseil

    Informations forums :
    Inscription : Octobre 2006
    Messages : 6 284
    Points : 11 743
    Points
    11 743
    Par défaut
    Je crains que les erreurs et les maladresses ne soient très nombreuses dans ton code :

    • le SELECT est interdit dans une fonction, sauf s'il alimente un curseur, des variables, ou encore s'il s'agit d'une sous-requête scalaire ; comme tu le mets entre parenthèses dans tes deux premières fonctions, c'est bien une sous-requête scalaire, et comme tu oublies les parenthèses sur la troisième fonction, c'est une erreur de syntaxe
    • ’’ ne veut rien dire ; ce caractère n'a pas de sens en SQL, d'où l'erreur sur ta quatrième fonction
    • il vaut mieux éviter d'utiliser "date" comme nom de paramètre, car c'est un mot réservé désignant le type DATE
    • dans un IF, il faut mettre un point-virgule après chaque instruction de résultat (ce qui pose des problèmes de séparateur... passons)
    • tu passes la date comme INT, tu la compares ensuite à une chaîne vide '' : ce n'est pas très cohérent ! de toute façon, il est plus simple d'utiliser le type DATE et donc les fonctions qui vont avec, comme DATEDIFF

    Je te propose la version suivante :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    CREATE FUNCTION age(naissance DATE, jour DATE) RETURNS INT
    RETURN DATEDIFF(COALESCE(jour, CURDATE()), naissance) DIV 365.25 ;
    Utilisation :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    -- un seul argument :
    select age('1980-01-31', NULL) ;
     
    -- deux arguments :
    select age('1980-01-31', '2009-02-22') ;
     
    -- idem, avec les arguments sous forme numérique
    select age(19800131, 20090222) ;
    Antoun
    Expert Tableau, Essbase, BO, SQL

    La bible d'Essbase, 2ème édition

  3. #3
    Membre actif Avatar de schwarzy2
    Femme Profil pro
    Développeur Web
    Inscrit en
    Septembre 2006
    Messages
    464
    Détails du profil
    Informations personnelles :
    Sexe : Femme
    Âge : 37
    Localisation : France

    Informations professionnelles :
    Activité : Développeur Web
    Secteur : High Tech - Multimédia et Internet

    Informations forums :
    Inscription : Septembre 2006
    Messages : 464
    Points : 288
    Points
    288
    Par défaut
    Merci Antoun pour ta réponse, je ne connais pas grand chose au SQL, je vais voir pour m'améliorer.
    En tout cas merci pour toutes explications, mais je ne peux pas mettre de NULL en deuxième argument car ce deuxième argument est une variable PHP, j'ai donc:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    SELECT age(c.naissanceamj,'$fin')
    Aussi même en ayant ma variable $fin égale à null, la valeur lue par SQL reste: '' et non NULL.

    Existe-t'il un moyen pour que la valeur lue soit NULL, ou dois-je modifier au contraire la fonction, pour que la valeur soit '' et non NULL?

    merci d'avance
    Feel good, feel geek

  4. #4
    Rédacteur/Modérateur

    Avatar de Antoun
    Homme Profil pro
    Architecte décisionnel
    Inscrit en
    Octobre 2006
    Messages
    6 284
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 54
    Localisation : France, Paris (Île de France)

    Informations professionnelles :
    Activité : Architecte décisionnel
    Secteur : Conseil

    Informations forums :
    Inscription : Octobre 2006
    Messages : 6 284
    Points : 11 743
    Points
    11 743
    Par défaut
    D'un point de vue purement théorique, si une variable qui est null en PHP devient une chaîne vide en SQL, ta façon de transmettre l'info est à revoir

    Néanmoins, si tu ne souhaites pas tout modifier pour une question de pure forme toute la question est de savoir ce que deviens ta chaîne vide lorsqu'elle est passée dans un argument de type DATE :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    CREATE FUNCTION test(d date) RETURNS date
    return d ;
     
    SELECT test('') ;
    On peut alors voir que le résultat est la "date zéro" '0000-00-00' (un concept propre à MySQL et pas vraiment orthodoxe, mais c'est un autre débat). On peut donc modifier ainsi la fonction :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
     
    -- avec COALESCE(NULLIF())
    CREATE FUNCTION age(naissance DATE, jour DATE) RETURNS INT
    RETURN DATEDIFF(COALESCE(NULLIF(jour, '0000-00-00'), CURDATE()), naissance) DIV 365.25 ;
     
    -- avec la fonction IF()
    CREATE FUNCTION age(naissance DATE, jour DATE) RETURNS INT
    RETURN DATEDIFF(IF(jour = '0000-00-00', CURDATE(), jour), naissance) DIV 365.25 ;
     
    --avec un CASE WHEN
    CREATE FUNCTION age(naissance DATE, jour DATE) RETURNS INT
    RETURN DATEDIFF(CASE jour WHEN '0000-00-00' THEN CURDATE() ELSE jour END, naissance) DIV 365.25 ;
    Antoun
    Expert Tableau, Essbase, BO, SQL

    La bible d'Essbase, 2ème édition

  5. #5
    Membre actif Avatar de schwarzy2
    Femme Profil pro
    Développeur Web
    Inscrit en
    Septembre 2006
    Messages
    464
    Détails du profil
    Informations personnelles :
    Sexe : Femme
    Âge : 37
    Localisation : France

    Informations professionnelles :
    Activité : Développeur Web
    Secteur : High Tech - Multimédia et Internet

    Informations forums :
    Inscription : Septembre 2006
    Messages : 464
    Points : 288
    Points
    288
    Par défaut
    ben pourtant ma façon de transmettre l'info est...tout ce qu'il y a de plus basique! voici mon code:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    $date_fin=save_date($_POST['fin']);
    if(!empty($date_fin)) $_SESSION['date_fin']=$date_fin;
    else $_SESSION['date_fin']=null; echo "null";
    (j'ai bien null qui s'affiche)
    puis j'ai :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    $fin=$_SESSION['date_fin'];
    	$ag=" SELECT age(c.naissanceamj,'$fin') as age";
    je ne vois pas où est le problème...???

    Mais merci beaucoup pour ta réponse, et d'indiquer en plus les différentes manières de faire, c'est vraiment sympa, ça me servira de support si l'occasion se représente!
    Feel good, feel geek

  6. #6
    Rédacteur/Modérateur

    Avatar de Antoun
    Homme Profil pro
    Architecte décisionnel
    Inscrit en
    Octobre 2006
    Messages
    6 284
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 54
    Localisation : France, Paris (Île de France)

    Informations professionnelles :
    Activité : Architecte décisionnel
    Secteur : Conseil

    Informations forums :
    Inscription : Octobre 2006
    Messages : 6 284
    Points : 11 743
    Points
    11 743
    Par défaut
    Le problème est que c'est un peu trop basique justement

    Perso, j'utilise en général une fonction d'encodage SQL, du genre :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    // $type doit être N (numérique), T (texte) ou D (date)
    CoderSQL($valeur, $type) {
      if ($valeur === NULL) return 'NULL' ;
      switch ($type) {
        case 'N' : return (float) $valeur ; break ;
        case 'T' : return str_replace("'", "''", $valeur) ; break ;
        case 'D' : return date("'Y-m-d'", $valeur) ; break ;
      }
    }
    C'est juste un exemple reconstitué de mémoire et non testé. En fait, le truc complet peut être plus compliqué, selon la confiance que j'accorde au type des variables PHP en entrée, et les types personnalisés que je peux ajouter (du genre "téléphone", "code postal", etc.)
    Antoun
    Expert Tableau, Essbase, BO, SQL

    La bible d'Essbase, 2ème édition

Discussions similaires

  1. [SQL] Conditions dans une requête SQL
    Par NeO666Linux dans le forum PHP & Base de données
    Réponses: 4
    Dernier message: 02/07/2007, 22h35
  2. condition dans une requete sql
    Par khayate dans le forum Langage SQL
    Réponses: 3
    Dernier message: 27/06/2007, 12h26
  3. Double condition dans une requete SQL
    Par quatar dans le forum Requêtes et SQL.
    Réponses: 5
    Dernier message: 29/05/2007, 16h22
  4. conditions dans une requete sql
    Par beve dans le forum Langage SQL
    Réponses: 2
    Dernier message: 04/05/2007, 14h29
  5. déclarer une table dans une fonction SQL
    Par bicho dans le forum VB.NET
    Réponses: 3
    Dernier message: 19/03/2007, 14h11

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