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

Rust Discussion :

[Rust] Gestion des erreurs


Sujet :

Rust

  1. #1
    Membre du Club
    Homme Profil pro
    aucun
    Inscrit en
    Mars 2014
    Messages
    55
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : aucun

    Informations forums :
    Inscription : Mars 2014
    Messages : 55
    Points : 42
    Points
    42
    Par défaut [Rust] Gestion des erreurs
    Bonjour/bonsoir je suis en apprentissage du langage Ruse mais j'ai du mal dans la gestion des erreurs exemple :

    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
    24
    25
     
    type MathResult = Result<f64, MathError>;
     
    fn div(x: f64, y: f64) -> MathResult {
            if y == 0.0 {
                // This operation would `fail`, instead let's return the reason of
                // the failure wrapped in `Err`
                Err(MathError::DivisionByZero)
            } else {
                // This operation is valid, return the result wrapped in `Ok`
                Ok(x / y)
            }
    }
     
    enum MathError {
            DivisionByZero,
            NegativeLogarithm,
            NegativeSquareRoot,
        }
     
    fn main(){
     
    div(10.0,20.0);
     
    }
    Si je comprends bien Ok et Err renvoient un objet de type Result mais je me suis demandé d'ou venais ces fonctions.

    Sur la documentation j'ai vu que le type Result<T, E> était un enum je ne sais pas complètement ce que c'est mais j'ai vu ça :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
     
    enum Result<T, E> {
       Ok(T),
       Err(E)
    }
    Je voudrais savoir en détail comment utiliser ces enum et la gestion des erreur que je ne comprends pas trop si je n'ai pas trop précisé certaine choses vous pouvez me demander en commentaire.

    Merci cordialement unoomad.

  2. #2
    Membre émérite
    Avatar de imperio
    Homme Profil pro
    Étudiant
    Inscrit en
    Mai 2010
    Messages
    852
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Ain (Rhône Alpes)

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

    Informations forums :
    Inscription : Mai 2010
    Messages : 852
    Points : 2 298
    Points
    2 298
    Par défaut
    La gestion des erreurs se fait effectivement via des enums, notamment Result. Ton code est bon dans l'ensemble. Pour vérifier si ta fonction a bien fonctionné, on fera ça :

    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
    24
    25
    #[derive(Debug)]
    enum MathError {
        DivisionByZero
    }
     
    type MathResult = Result<f64, MathError>;
     
    fn div(x: f64, y: f64) -> MathResult {
        if y == 0.0 {
            // This operation would `fail`, instead let's return the reason of
            // the failure wrapped in `Err`
            Err(MathError::DivisionByZero)
        } else {
            // This operation is valid, return the result wrapped in `Ok`
            Ok(x / y)
        }
    }
     
    fn main() {
        println!("{:?}", div(1f64, 2f64)); // -> affiche Ok(0.5)
        match div(1f64, 0f64) {
            Ok(value) => println!("Ça s'est bien passé : {}", value),
            Err(err) => println!("Une erreur est arrivée : {:?}", err)
        };
    }
    On obtient la valeur contenue dans l'enum en matchant dessus. Comme je l'ai dit dans le cours, tu peux aussi utiliser la méthode unwrap :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    fn main() {
        println!("{}", div(1f64, 2f64).unwrap()); // -> affiche 0.5
        println!("{}", div(1f64, 0f64).unwrap()); // -> va planter
    }
    Mais c'est à tes risques et périls. J'espère avoir répondu à tes questions.

  3. #3
    Membre du Club
    Homme Profil pro
    aucun
    Inscrit en
    Mars 2014
    Messages
    55
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : aucun

    Informations forums :
    Inscription : Mars 2014
    Messages : 55
    Points : 42
    Points
    42
    Par défaut
    Donc si j'ai bien compris pour la gestion d'erreur d'un coté on doit "emballer" grace a la fonction Ok ou Err et verifier grâce au pattern maching si le résultat est bon ou si il y a une erreur c'est ça ? Ce que je ne comprends pas c'est que ces deux fonctions font 2 choses differente on dirait l'utilisation de Ok dans la fonction div n'est pas la même que dans le pattern matching dans le main c'est ça qui me bloque un peu ...


    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
     
    match div(1f64, 0f64) {
            Ok(value) => println!("Ça s'est bien passé : {}", value),
            Err(err) => println!("Une erreur est arrivée : {:?}", err)
        };
    Ce que je me demande ici c'est comment il sais si c'est dans Ok ou Err qu'il doit aller, c'est grace a l'objet du type Result<f64, MathError> ?
    Quand c'est Ok la fonction div renvoie un truc du genre Result<0.5, ()> et si c'est Err ça renvoie ça Result<(), DivisionByZero> ?

  4. #4
    Membre émérite
    Avatar de imperio
    Homme Profil pro
    Étudiant
    Inscrit en
    Mai 2010
    Messages
    852
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Ain (Rhône Alpes)

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

    Informations forums :
    Inscription : Mai 2010
    Messages : 852
    Points : 2 298
    Points
    2 298
    Par défaut
    Ah ça y est, j'ai compris ton problème ! Ok et Err sont des enums, mais un peu particulières : ce sont des structures tuples. En gros ce sont des éléments d'enums qui contiennent une valeur. Je reprends mon exemple du cours :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    struct Distance(isize);
     
    let distance = Distance(23);
     
    let Distance(longueur) = distance;
    println!("La distance est {}", longueur);
    On pourrait faire un truc avec un Result dans ce genre :

    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
    struct Distance(i32);
     
    fn get_distance(dist: i32) -> Result<Distance, String> {
        if dist < 0 {
            Err("Distance invalide".to_owned())
        } else {
            Ok(Distance(dist))
        }
    }
     
    // et maintenant on match dessus pour récupérer la valeur :
    match get_distance(23) {
        Ok(Distance(d)) => println!("La distance est {}", d),
        Err(e) => println!("erreur : {}", e)
    };
    On aurait aussi pu faire comme ça pour récupérer la valeur :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    let distance = get_distance(23).unwrap();
    // ici on a donc distance qui vaut Distance(23)
    // Pour récupérer la valeur :
    match distance {
        Distance(d) => println!("La distance est {}", d)
    };
    Tu comprends un peu mieux comment ça fonctionne ?

  5. #5
    Membre du Club
    Homme Profil pro
    aucun
    Inscrit en
    Mars 2014
    Messages
    55
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : aucun

    Informations forums :
    Inscription : Mars 2014
    Messages : 55
    Points : 42
    Points
    42
    Par défaut
    Ahh c'est bon j'ai compris je pensais que c'était quelque chose différent des structs mais dernière chose si c'est des enum on est pas sensé les utilisés comme ça ?
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
     
    #[derive(Debug)]
    enum MathError {
        DivisionByZero(i8)
    }
    fn main(){
     
        let division = MathError::DivisionByZero(8);
        let MathError::DivisionByZero(val) = MathError::DivisionByZero(8);
        println!("{}", val);
     
    }

    Pourquoi Ok et Err n'ont pas de préfixe ?

  6. #6
    Membre émérite
    Avatar de imperio
    Homme Profil pro
    Étudiant
    Inscrit en
    Mai 2010
    Messages
    852
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France, Ain (Rhône Alpes)

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

    Informations forums :
    Inscription : Mai 2010
    Messages : 852
    Points : 2 298
    Points
    2 298
    Par défaut
    Parce qu'ils sont déjà importés "par défaut". Dans ton cas tu peux faire :

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    #[derive(Debug)]
    enum MathError {
        DivisionByZero(i8)
    }
     
    use MathError::DivisionByZero;
     
    fn main(){
     
        let division = DivisionByZero(8);
        let DivisionByZero(val) = DivisionByZero(8);
        println!("{}", val);
    }
    Cependant je préfère avec les préfixes.

  7. #7
    Membre du Club
    Homme Profil pro
    aucun
    Inscrit en
    Mars 2014
    Messages
    55
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Localisation : France

    Informations professionnelles :
    Activité : aucun

    Informations forums :
    Inscription : Mars 2014
    Messages : 55
    Points : 42
    Points
    42
    Par défaut
    Ah je vois tout est clair maintenant je résous ce post, la je travaille sur les références et variable avant de poser d'autre question dessus ... Merci a toi.

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

Discussions similaires

  1. [FB] Gestion des erreurs et application francophone
    Par Benjamin GAGNEUX dans le forum Installation
    Réponses: 10
    Dernier message: 20/05/2006, 14h54
  2. [struts][Datasource]Gestion des erreurs
    Par GreenJay dans le forum Struts 1
    Réponses: 8
    Dernier message: 15/09/2004, 16h51
  3. [VB6] Gestion des erreurs dans une dll
    Par zimba-tm dans le forum VB 6 et antérieur
    Réponses: 8
    Dernier message: 02/08/2004, 11h20
  4. [XSLT]Est ce qu'il y'a la gestion des erreur en xslt ?
    Par miloud dans le forum XSL/XSLT/XPATH
    Réponses: 2
    Dernier message: 04/02/2004, 17h19
  5. [LG]gestion des erreurs
    Par frontin dans le forum Langage
    Réponses: 3
    Dernier message: 29/11/2003, 22h41

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