In Ihrem Fall die type switch ist die einfachste und bequemste Lösung:
func name(v interface{}) {
switch x := v.(type) {
case []MyInterface:
fmt.Println("[]MyInterface, len:", len(x))
for _, i := range x {
fmt.Println(i)
}
case MyInterface:
fmt.Println("MyInterface:", x)
default:
fmt.Printf("Unsupported type: %T\n", x)
}
}
Die case
Zweige aufzählen die möglichen Typen, und in ihnen die x
Variable wird bereits von diesem Typ sein, so können Sie es verwenden damit.
Testing es:
type MyInterface interface {
io.Writer
}
var i MyInterface = os.Stdout
name(i)
var s = []MyInterface{i, i}
name(s)
name("something else")
Output (versuchen Sie es auf dem Go Playground):
MyInterface: &{0x1040e110}
[]MyInterface, len: 2
&{0x1040e110}
&{0x1040e110}
Unsupported type: string
Für einen einzigen Typ überprüfen Sie auch type assertion verwenden:
if x, ok := v.([]MyInterface); ok {
// x is of type []MyInterface
for _, i := range x {
fmt.Println(i)
}
} else {
// x is not of type []MyInterface or it is nil
}
Es gibt auch andere Möglichkeiten, mit Paket reflect
können Sie eine allgemeine (und schreiben langsamere) Lösung, aber wenn du gerade Go startest, solltest du noch nicht ins Nachdenken vertiefen.
Eigentlich ist mein Problem, dass v ein Stück Zeiger ist. Nach einigem Nachforschen denke ich, dass es besser ist, über die Sammlung an erster Stelle zu iterieren, zumindest die Implementierung, die ich gesehen habe, verwendete einen solchen Ansatz. Einige Copy/Paste-Boilerplate-Code, aber ich denke, es wird kein Problem für jetzt – Alexander