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

Python Discussion :

Sortie de fonction sans utiliser return


Sujet :

Python

  1. #1
    Membre averti
    Homme Profil pro
    Inscrit en
    Septembre 2011
    Messages
    17
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Seine et Marne (Île de France)

    Informations forums :
    Inscription : Septembre 2011
    Messages : 17
    Par défaut Sortie de fonction sans utiliser return
    Bonjour à tous ! Arpès un petit tour des tutos/cours et des différents sujets du forum, je n'ai pas trouvé de réponse à ma question (que je pensais pourtant simple :/), à savoir : Comment peut-on demander à une fonction de retourner une chaine de caractère SANS utiliser return ? Je n'ai pu trouver que des explications conernant print (qui affiche mais ne retourne rien) et inpout/output (qui n'ont rien à voir). Existe t'il un mot magique ayant le même effet que return mais SANS sortir de la fonction ?

    Pour préciser un peu ma question et son contexte voila le bout de code concernant cette fonction :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    def Instance(name, UD, type, size):
        if type == 'NP':
            return Message(name,UD,type,size,0)
     
        if type == 'P':
            k = 0
            period = 20
            time = 0
            while k<15:
                return Message(name,UD,type,size,time)
                time += period
                k += 1
    Il s'agit donc d'une fonction censée renvoyer soit une seule occurence de Message(xxx,xxx,xxx,xxx), soit 15 (le nombre n'a ici aucune importance). Cependant dans le cas "P", le return fait stopper la fonction immédiatement après avoir renvoyé une seule fois le "Message(xxx,xxx,xxx,xxx)".

    Au cas où la possibilité d'avoir plusieurs retours avec un seule occurence de la fonction serait impossible, comment puis-je m'y prendre pour atteindre mon but ?

    Merci d'avance de vos réponses !

  2. #2
    Membre Expert Avatar de plxpy
    Homme Profil pro
    Ingénieur géographe
    Inscrit en
    Janvier 2009
    Messages
    792
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 60
    Localisation : France, Haute Garonne (Midi Pyrénées)

    Informations professionnelles :
    Activité : Ingénieur géographe
    Secteur : Aéronautique - Marine - Espace - Armement

    Informations forums :
    Inscription : Janvier 2009
    Messages : 792
    Par défaut
    J'avoue avoir du mal à me pencher sur le fond du problème quand la forme me fait bondir.

    Appeler une fonction Instance est quand même particulièrement tordu !

  3. #3
    Membre émérite
    Profil pro
    Inscrit en
    Mars 2005
    Messages
    625
    Détails du profil
    Informations personnelles :
    Localisation : France

    Informations forums :
    Inscription : Mars 2005
    Messages : 625
    Par défaut
    Et sinon yield semble être exactement ce que tu cherches
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
     
    def f():
        x = 1
        while x<5:
            out = '*' * x
            yield out
            x += 1
     
    for i in f():
        print i

  4. #4
    Membre averti
    Homme Profil pro
    Inscrit en
    Septembre 2011
    Messages
    17
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Seine et Marne (Île de France)

    Informations forums :
    Inscription : Septembre 2011
    Messages : 17
    Par défaut
    @Petitbidon : Apparement ce yield correspond bien à ce que je cherche, mais après un essai rapide il me renvoie ce qui ressemble à des adresses (<generator object at 0x2aae810292d8>), je vais me renseigner pour voir comment m'en servir. Merci pour cette piste !

    @pixpy : Je n'ai pas compris ta remarque, le nom de ma fonction à été choisi arbitrairement. Je suis grand débutant en Python et je dois apprendre à m'en servir sans rentrer dans les subtilités (contrainte de temps oblige), peut-être voulait tu dire qu'il existe quelquechose appellé instance dans ce langage, mais si c'est le cas c'est seulement une coincidence, tu peux remplacer le nom de la fonction par banane si le coeur t'en dit !

  5. #5
    Membre très actif
    Avatar de afranck64
    Homme Profil pro
    Étudiant
    Inscrit en
    Janvier 2009
    Messages
    592
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 34
    Localisation : Cameroun

    Informations professionnelles :
    Activité : Étudiant
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Janvier 2009
    Messages : 592
    Par défaut
    Citation Envoyé par Thibqult Voir le message
    @Petitbidon : Apparement ce yield correspond bien à ce que je cherche, mais après un essai rapide il me renvoie ce qui ressemble à des adresses (<generator object at 0x2aae810292d8>), je vais me renseigner pour voir comment m'en servir.
    vous pouvez vous en servir comme itérateur:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    for obj in generator:
       print obj
    Win 10 64 bits / Linux Mint 18, - AMD A6 Quad: Py27 / Py35
    CONTENU D'UNE QUESTION
    Exemples:
    - Configuration (système d'exploitation, version de Python et des bibliothèques utilisées)
    - Code source du morceau de programme où il y a un bogue
    - Ligne de code sur laquelle le bogue apparaît
    - Erreur complète retournée pas l'interpréteur Python
    - Recherche déjà effectuée (FAQ, Tutoriels, ...)
    - Tests déjà effectués

  6. #6
    Membre Expert Avatar de plxpy
    Homme Profil pro
    Ingénieur géographe
    Inscrit en
    Janvier 2009
    Messages
    792
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 60
    Localisation : France, Haute Garonne (Midi Pyrénées)

    Informations professionnelles :
    Activité : Ingénieur géographe
    Secteur : Aéronautique - Marine - Espace - Armement

    Informations forums :
    Inscription : Janvier 2009
    Messages : 792
    Par défaut
    peut-être voulait tu dire qu'il existe quelquechose appellé instance dans ce langage
    Effectivement. En POO (Programmation Orientée Objet, en Python ou dans d'autres langages), une instance (de classe) est un objet (toujours au sens POO) d'une classe. Donc quand je vois "Instance" pour une fonction, mon sang ne fait qu'un tour.

    C'est, par exemple, du même style que d'appeler une fonction "module", "package" ou "method" (qui ont aussi une signification bien particulière en Python).

    Si tu es débutant en Python (aussi en POO ?), OK.

    Mais l'un des atouts de Python est d'être généralement plus lisible que d'autres langages aussi, si des termes inappropriés sont utilisés, ça part un peu en vrille et on risque de ne plus trop y comprendre grand-chose.

    tu peux remplacer le nom de la fonction par banane si le coeur t'en dit
    A choisir entre les deux, je préfère effectivement banane ! Mais bon, il y a tellement d'autres possibilités ...

  7. #7
    Membre Expert Avatar de PauseKawa
    Homme Profil pro
    Technicien Help Desk, maintenance, réseau, système et +
    Inscrit en
    Juin 2006
    Messages
    2 725
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Hérault (Languedoc Roussillon)

    Informations professionnelles :
    Activité : Technicien Help Desk, maintenance, réseau, système et +
    Secteur : High Tech - Éditeur de logiciels

    Informations forums :
    Inscription : Juin 2006
    Messages : 2 725
    Par défaut
    Bonjour,

    Sortie de fonction sans utiliser return: En python une fonction retourne toujours quelque chose, les procédures n'existent pas.
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    >>> def Foo():
    ...     pass
    ... 
    >>> f = Foo()
    >>> f
    >>> print(f)
    None
    >>>
    Une fonction dont on ne précise pas de valeur de retour revoie None.
    Un petit tour au cœur de la mécanique le montre:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    >>> dis.dis(Foo)
      2           0 LOAD_CONST               0 (None)
                  3 RETURN_VALUE
    Mais bon, retenez juste cela: En Python une fonction retourne toujours quelque chose en Python. Cela vous éviteras des surprises (None)

    Citation Envoyé par Thibqult Voir le message
    Existe t'il un mot magique ayant le même effet que return mais SANS sortir de la fonction ?
    C'est effectivement yield et celui ci est un générateur.
    Vous pouvez l'utiliser avec for qui fait une itération ou tout simplement avec .next()
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    >>> def Foo():
    ...    yield 1
    ... 
    >>> f = Foo()
    >>> f
    <generator object Foo at 0xb748e57c>
    >>> f.next()
    1
    Le problème c'est que dans le cas de
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
        if type == 'NP':
            return Message(name,UD,type,size,0)
    Vous avez une fonction 'classique' et dans le cas de
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
        elif type == 'P':
            k = 0
            period = 20
            time = 0
            while k<15:
                yield Message(name,UD,type,size,time)
                time += period
                k += 1
    Vous transformez votre fonction en générateur.
    Dans ce cas vous devrez tester ce que retourne la fonction pour savoir comment la traiter.
    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
    def bananne(name, UD, type, size):
        if type == 'NP':
            return Message(name,UD,type,size,0)
     
        if type == 'P':
            k = 0
            period = 20
            time = 0
            while k<15:
                yield Message(name,UD,type,size,time)
                time += period
                k += 1
     
    b = bananne()
    if b = ...
    etc...
    Vous devrez donc tester le type de l'objet retourné par la fonction.
    Pas tout simple cela pour vous non ?...

    Pourquoi ne pas faire simple à votre niveau (ce n'est pas péjoratif)
    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
    def BananneNP(name, UD, type, size):
        return Message(name,UD,type,size,0)
     
    def BananneP(name, UD, type, size):
        k = 0
        period = 20
        time = 0
        retour = []
        while k<15:
            retour.append(Message(name,UD,type,size,time))
            time += period
            k += 1
        return retour
     
    if type == 'NP':
        result = BananneNP(name, UD, type, size)
    elif if type == 'P':
        result = BananneP(name, UD, type, size)
    @+

    Edit: Et pour ce qui est de yield il ne sort pas de la fonction, c'est la fin du bloc de code qui en sort.

  8. #8
    Membre averti
    Homme Profil pro
    Inscrit en
    Septembre 2011
    Messages
    17
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Seine et Marne (Île de France)

    Informations forums :
    Inscription : Septembre 2011
    Messages : 17
    Par défaut
    Plxpy -> Merci pour cette explication, il s'agissait donc bien d'une erreur involontaire. Pour répondre à ta question je bidouille un peu en C++ donc j'ai quelques notions de POO, mais je n'avais jamais eu à traiter avec le terme d'isntance jusqu'ici. Maintenant je saurais qu'il faut s'en méfier

    PauseKawa -> Merci pour ta réponse très complète, en effet la seconde facon de faire est plus compréhensible pour moi et fonctionne parfaitement (ce qui fait plaisir puisqu'effectivement j'avais rencontré quelques problèmes avec des renvois de none en utilisant yield...).

    Merci à tous de votre aide !

    PS : Au cas ou certains tomberaient sur cette discussion et souhaiteraient plus d'informatiuons sur yield, je vous renvoie sur cette discussion http://www.developpez.net/forums/d55...-yield-python/ qui contient deux exemples assez bien foutus.

+ Répondre à la discussion
Cette discussion est résolue.

Discussions similaires

  1. Réponses: 2
    Dernier message: 05/03/2012, 16h31
  2. Réponses: 4
    Dernier message: 28/05/2008, 16h35
  3. Réponses: 1
    Dernier message: 06/12/2007, 19h42
  4. [Mail] Envoi d'e-mail sans utiliser la fonction mail()
    Par the_hardgamer dans le forum Langage
    Réponses: 1
    Dernier message: 10/08/2007, 16h10
  5. Réponses: 11
    Dernier message: 18/02/2007, 23h20

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