Home > other >  TypeOf with Comparable in errors.Is
TypeOf with Comparable in errors.Is

Time:01-17

I am learning how error comparison works in Go and found something I cannot understand.

Function errors.Is(err, target error) checks if target is Comparable.

func Is(err, target error) bool {
    if target == nil {
        return err == target
    }

    isComparable := reflectlite.TypeOf(target).Comparable()
    for {
        if isComparable && err == target {
            return true
        }

Source

Which case does this call handle given that all interfaces in Go are comparable and error is an interface?

CodePudding user response:

Interfaces values are comparable, but the comparison can panic at run-time. The specification says:

A comparison of two interface values with identical dynamic types causes a run-time panic if values of that type are not comparable.

The check prevents a panic by skipping the comparison when the target's concrete type is not comparable.

Here's an example:

type E []byte
func (e E) Error() string { return string(e) }
func (e E) Is(target error) bool {
    t, ok := target.(E)
    return ok && bytes.Equal(e, t)
}

var a error = E{}
var b error = E{}
fmt.Println(errors.Is(a, b)) // prints true
fmt.Println(a == b)          // panics because slices are not comparable
  •  Tags:  
  • Related