简体   繁体   English

Go 中没有反射的动态检查的最佳模式?

[英]Best patterns for dynamic checks in Go without reflection?

Any chance there are good patterns in any of our codebases that help reduce redundant checks on typed fields/structs?我们的任何代码库中是否存在有助于减少对类型化字段/结构的冗余检查的良好模式? I feel like Lisp handles these things well, but trying to understand if there are any good patterns without the need for something like reflection, etc.我觉得 Lisp 可以很好地处理这些事情,但试图了解是否有任何好的模式而不需要像反射等东西。

For example, for custom structs, I find myself needing to do a lot of:例如,对于自定义结构,我发现自己需要做很多事情:

type helloworld struct {
 field1 *string
 field2 *string
 field3 int
}
if field1 != nil { 
  if len([]rune(*field1)) > MAX_ALLOWED_LEN) return errors.New("exceeded max allowable length")
}
if field2 != nil { 
  if len([]rune(*field2)) > MAX_ALLOWED_LEN) return errors.New("exceeded max allowable length")
}
if field3 != 0 { //do stuff}
....

maps are great, but typing can be too generic a lot of the time, which can also cause confusion.地图很棒,但很多时候打字可能过于笼统,这也会引起混乱。 I ask, because some of these checks are redundant and proliferate through a lot of packages, so when I need to add an additional field, refactoring is time consuming.我问,因为其中一些检查是多余的,并且通过很多包扩散,所以当我需要添加额外的字段时,重构是耗时的。 It would be nice if I have validation on certain types or fields while keeping performance high.如果我在保持高性能的同时对某些类型或字段进行验证,那就太好了。

3 directions, not the most straight forward, but they can reduce your check blocks: 3个方向,不是最直接的,但它们可以减少你的检查块:

Method 1: Define your own annotation方法一:定义自己的注解

Golang has annotations in structs Golang 在结构中有注解

type bla struct {
  t string `json:"some,omitempty"`
}

This is actually an open annotation structure (tags).这实际上是一个开放的注释结构(标签)。

A nice example (contains some reflection) is https://github.com/mitchellh/mapstructure一个很好的例子(包含一些反射)是https://github.com/mitchellh/mapstructure

Look at line 374 of the mapstructure.go file.查看 mapstructure.go 文件的第 374 行。 It is pretty re-usable, and you could use it as base for your own annotation.它非常可重用,您可以将其用作您自己的注释的基础。

To use it in your context you would create types which you can then parse.要在您的上下文中使用它,您将创建然后可以解析的类型。

Method 2: DRY check function方法二:干检 function

Your check seems to be the same or similar.您的支票似乎相同或相似。

A generic comparator which iterates over fields:遍历字段的通用比较器:

func check(fields ...interface{}) error {
  for v:=range fields {
    if v==nil {
      return errors.New("nil")
    }
    switch v.type() {
      case *string:
        if len([]rune(*v)) > MAX_ALLOWED_LEN) {
          return errors.New("exceeded max allowable length")
        }
      }
      ...
    }
}

Method 3: Generics.方法3:Generics。

The switch type in method 2 might be able to be rewritten in a generic style.方法 2 中的 switch 类型可能能够以通用样式重写。 Not easier, but can be prettier.不是更容易,但可以更漂亮。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM