Maison >développement back-end >Golang >Une brève analyse de la façon d'implémenter l'énumération dans Golang (avec code)

Une brève analyse de la façon d'implémenter l'énumération dans Golang (avec code)

青灯夜游
青灯夜游avant
2022-02-04 09:00:315520parcourir

Comment implémenter l'énumération dans Golang ? L'article suivant vous présentera la méthode de mise en œuvre de l'énumération dans Golang J'espère qu'il vous sera utile !

Une brève analyse de la façon d'implémenter l'énumération dans Golang (avec code)

Dans le domaine de la programmation, les énumérations sont utilisées pour représenter des types qui ne contiennent qu'un nombre limité de valeurs fixes. Elles sont généralement utilisées en développement pour identifier des codes d'erreur ou des machines à états. Prenons comme exemple la machine à états d'un objet entité. Elle correspond généralement à la valeur du champ qui identifie l'état de l'enregistrement correspondant de cet objet dans la base de données. [Recommandation connexe : Tutoriel vidéo Go]

Lorsque vous avez commencé à apprendre la programmation, vous devez avoir écrit, ou au moins vu, du code qui utilise directement des nombres magiques pour porter des jugements. Qu'est-ce qu'un nombre magique ? Par exemple, lorsque vous souhaitez épingler un article en haut, vous devez d'abord déterminer si l'article a été publié.

if (article.state == 2) {
   // state 2 代表文章已发布
}

S'il n'y a pas de commentaires dans notre code, ou lorsque le code de notre projet est rempli de ces jugements de nombres magiques, aurez-vous mal à la tête ?

Plus tard, j'ai appris à définir ces valeurs d'état comme des constantes, et j'ai également développé une méthode pour déterminer l'état de l'objet afin d'encapsuler cette logique séparément.

public class ArticleState {
    
    public static final int Draft = 1; //草稿
    
    public static final int Published = 2; //发布
    
    public static final int Deleted = 3; // 已删除
}

public  Boolean checkArticleState(int state) {
    
    ...
    
}

Cette utilisation est certainement bien meilleure que d'utiliser directement des nombres magiques pour porter des jugements dans le programme. Au moins, cela ne vous donnera pas mal à la tête ou ne vous donnera pas envie de maudire.

Cependant, le grand frère qui m'a emmené là-bas a dit que cette méthode avait aussi des défauts. La méthode checkArticleState ci-dessus est utilisée pour vérifier l'état de l'article. Elle est destinée à laisser passer l'appelant dans l'une des trois constantes statiques de ArticleState, mais comme il n'y a pas de contrainte de type, la transmission de n'importe quelle valeur int est syntaxiquement autorisée et le compilateur n'émettra aucun avertissement. Il est plus approprié d'utiliser une énumération.

em~ ! Je ne me souviens pas que le professeur ait parlé de cette chose pendant le semestre où j'enseignais Java à l'université. Serait-ce un autre point de connaissance que j'ai manqué en jouant sur mon téléphone portable en classe ? Ainsi, après avoir utilisé l'énumération, notre code Java devient :

// 使用enum而非class声明
public enum ArticleState {
	
    //要在enum里创建所有的枚举对象
    Draft(1, "草稿");
    Published(2, "已发布");
    Deleted(3, "已删除")
      
    // 自定义属性
    private int code;

    private String text;
  
    // 构造方法必须是private的
    ArticleState(int code, String text) {
        this.code = id;
        this.text = name;
    }
}

public  Boolean checkArticleState(ArticleState state) {
    
    ...
    
}

De cette façon, nous pouvons compter sur le type d'énumération du paramètre formel pour nous aider à filtrer les valeurs d'état illégales lors du passage de la valeur entière en tant que paramètre à la méthode checkArticleState. le type ne correspond pas. Si la compilation échoue, le compilateur vous le demandera immédiatement lors de l'écriture du code.

Si vous n’avez jamais utilisé Java auparavant, ne vous inquiétez pas, j’ai marqué les principaux points grammaticaux avec des commentaires, et tout le monde devrait pouvoir le comprendre.

Au cours des deux dernières années, j'ai principalement utilisé Go pour réaliser des projets. J'ai découvert que des problèmes similaires existaient dans Go, mais Go ne fournissait pas de types d'énumération. Alors, comment limiter correctement la valeur de statut ? Cela ne fonctionnera certainement pas si vous utilisez toujours des constantes de type int. Par exemple :

 const (
     Draft int = 1
     Published = 2
     Deleted   = 3
 )

 const (
     Summer int = 1
     Autumn     = 2
     Winter     = 3
     Spring     = 4
 )

 func main() {
     // 输出 true, 不会有任何编译错误
     fmt.Println(Autumn == Draft)
 }

Par exemple, deux ensembles de constantes de type int sont définis ci-dessus, l'un représente le statut de l'article et l'autre représente les quatre saisons. Il n'y aura aucune erreur de compilation lors de la comparaison du statut de l'article avec les saisons de cette façon.

La réponse peut être trouvée dans le code des bibliothèques intégrées de Go ou dans certaines bibliothèques open source que nous connaissons tous. Par exemple, si vous regardez comment les codes d'erreur gRPC sont définis dans google.golang.org/grpc/codes, vous pouvez comprendre comment implémenter correctement l'énumération.

Nous pouvons utiliser int comme type de base pour créer un type d'alias. Go prend en charge cela

type Season int

const (
	Summer Season = 1
	Autumn        = 2
	Winter        = 3
	Spring        = 4
)

Bien sûr, Go utilise souvent iota lors de la définition de valeurs constantes continues, de sorte que la définition ci-dessus peut être encore simplifiée.

type Season int

const (
	Summer Season = iota + 1
	Autumn
	Winter
	Spring
)

type ArticleState int

const (
  Draft int = iota + 1
  Published
  Deleted  
)

func checkArticleState(state ArticleState) bool {
	// ... 
}

 func main() {
   // 两个操作数类型不匹配,编译错误
   fmt.Println(Autumn == Draft)
	// 参数类型不匹配,但是因为 ArticleState 底层的类型是 int 所以传递 int 的时候会发生隐式类型转换,所以不会报错
   checkArticleState(100)
 }

Bien que les types sous-jacents de ces valeurs d'état soient tous des valeurs int, la comparaison désormais des valeurs d'énumération de deux types non liés entraînera des erreurs de compilation, car il existe désormais des restrictions de type partout où nous utilisons des valeurs d'état.

Cependant, le type de paramètre de la fonction checkArticleState est défini sur ArticleState car le type sous-jacent de ArticleState est int. Par conséquent, lors de l'appel de checkArticleState, la transmission des paramètres de type int entraînera une conversion de type implicite et ne provoquera pas d'erreur de compilation. Si vous souhaitez résoudre ce problème, vous pouvez uniquement redéfinir le type pour y parvenir

Vous pouvez vous référer à cette réponse. sur StackOverflow :

https://stackoverflow.com/questions/50826100/how-to-disable-implicit-type-conversion-for-constants

Pour plus de connaissances sur la programmation, veuillez visiter : Vidéo de programmation ! !

Ce qui précède est le contenu détaillé de. pour plus d'informations, suivez d'autres articles connexes sur le site Web de PHP en chinois!

Déclaration:
Cet article est reproduit dans:. en cas de violation, veuillez contacter admin@php.cn Supprimer