Go exige d'utiliser une variable définie au moins une fois : ça implique la solution que tu proposes, au détail près qu'il n'y a pas de garantie qu'on n'utilise pas malgré tout la valeur retournée par la suite.
Ce n'est pas évident d'imposer mieux au niveau du langage. En Go les erreurs sont juste une valeur comme les autres, elles ne sont pas traités spécialement par le compilateur ou le langage : il s'agit juste de conventions et d'une interface error prédéfinie au même titre que d'autres types prédéfinis (comme int).
La façon classique d'empêcher à 99% (à unwrap ou exception près) d'utiliser une valeur retournée malgré une erreur, c'est les types option et filtrage par motifs qu'on trouve dans les langages avec des types algébriques (OCaml, Rust, etc.).
En Go, on a l'obligation d'utiliser au moins une fois err et, ensuite, on peut chercher plus de garanties avec des analyses statiques heuristiques (comme errcheck), indépendantes du langage avec risque de faux positifs et négatifs. En pratique, d'après l'institut de statistiques pifométriques, ça empêche uniquement 98% des problèmes (contre 99% avec OCaml ou Rust), mais permet en échange de conserver un typage simple et de ne pas forcer une imbrication du flot de contrôle. Ce n'est pas un problème facile : en cas d'erreurs imbriquées, l'approche des types option et filtrage par motifs demande, soit du sucre syntaxique ad hoc comme en Rust ou Elixir (comme ? ou with qui encouragent à traiter uniquement le chemin où tout se passe bien), soit des concepts avancés comme les monades en Haskell ou des réimplémentions ad hoc de celles-ci. Autrement, ça peut devenir difficile à lire et maladroit.
C'est toute la question des avantages et désavantages entre algorithmes de recherche de solution approchée (souvent plus simples et plus rapides au prix de ne pas offrir de garantie absolue) et algorithmes de recherche de solution exacte (plus lents et conduisent souvent à plus de complexité).
Ceci dit, avec les deux approches, rien ne garantie, par contre, que l'erreur est gérée proprement (d'un point de vue sémantique), ce qui arrive plus souvent en pratique et est un problème bien plus difficile qui ne peut être traité par les types que dans les langages avec types dépendants comme Coq.
[^] # Re: Raisons d'essayer Rust
Posté par anaseto . En réponse au journal Retour d'expérience sur les langages de programmation. Évalué à 4.
Go exige d'utiliser une variable définie au moins une fois : ça implique la solution que tu proposes, au détail près qu'il n'y a pas de garantie qu'on n'utilise pas malgré tout la valeur retournée par la suite.
Ce n'est pas évident d'imposer mieux au niveau du langage. En Go les erreurs sont juste une valeur comme les autres, elles ne sont pas traités spécialement par le compilateur ou le langage : il s'agit juste de conventions et d'une interface
errorprédéfinie au même titre que d'autres types prédéfinis (commeint).La façon classique d'empêcher à 99% (à unwrap ou exception près) d'utiliser une valeur retournée malgré une erreur, c'est les types option et filtrage par motifs qu'on trouve dans les langages avec des types algébriques (OCaml, Rust, etc.).
En Go, on a l'obligation d'utiliser au moins une fois
erret, ensuite, on peut chercher plus de garanties avec des analyses statiques heuristiques (comme errcheck), indépendantes du langage avec risque de faux positifs et négatifs. En pratique, d'après l'institut de statistiques pifométriques, ça empêche uniquement 98% des problèmes (contre 99% avec OCaml ou Rust), mais permet en échange de conserver un typage simple et de ne pas forcer une imbrication du flot de contrôle. Ce n'est pas un problème facile : en cas d'erreurs imbriquées, l'approche des types option et filtrage par motifs demande, soit du sucre syntaxique ad hoc comme en Rust ou Elixir (comme?ouwithqui encouragent à traiter uniquement le chemin où tout se passe bien), soit des concepts avancés comme les monades en Haskell ou des réimplémentions ad hoc de celles-ci. Autrement, ça peut devenir difficile à lire et maladroit.C'est toute la question des avantages et désavantages entre algorithmes de recherche de solution approchée (souvent plus simples et plus rapides au prix de ne pas offrir de garantie absolue) et algorithmes de recherche de solution exacte (plus lents et conduisent souvent à plus de complexité).
Ceci dit, avec les deux approches, rien ne garantie, par contre, que l'erreur est gérée proprement (d'un point de vue sémantique), ce qui arrive plus souvent en pratique et est un problème bien plus difficile qui ne peut être traité par les types que dans les langages avec types dépendants comme Coq.