445 Stimmen

Wie man den lästigen Fehler "deklariert und nicht verwendet" vermeidet

Ich lerne Go, aber ich finde es ein bisschen ärgerlich, dass ich beim Kompilieren keine ungenutzten Variablen oder Pakete hinterlassen sollte.

Dies bremst mich wirklich ziemlich aus. Zum Beispiel wollte ich nur ein neues Paket deklarieren und plante, es später zu verwenden, oder nur einige Befehle auskommentieren, um sie zu testen. Ich bekomme immer den Fehler und muss alle diese Verwendungen auskommentieren.

Gibt es einen Weg, um diese Art von Überprüfung in Go zu vermeiden?

364voto

Florent Bayle Punkte 11114

Dieser Fehler soll dich dazu zwingen, besseren Code zu schreiben, und sicherstellen, dass du alles verwendest, was du deklarierst oder importierst. Es erleichtert das Lesen von Code, der von anderen Personen geschrieben wurde (du kannst immer sicher sein, dass alle deklarierten Variablen verwendet werden), und vermeidet möglichen "dead code".

Aber wenn du diesen Fehler wirklich überspringen möchtest, kannst du das Platzhalter-Identifikator (_) verwenden:

package main

import (
    _ "fmt" // importiert und nicht verwendet: "fmt"
)

func main() {
    i := 1 // i deklariert und nicht verwendet
}

wird zu

package main

import (
    _ "fmt" // kein Fehler mehr
)

func main() {
    i := 1 // kein Fehler mehr
    _ = i
}

Wie kostix unten in den Kommentaren erwähnt hat, findest du die offizielle Position des Go-Teams in den FAQ:

Das Vorhandensein einer ungenutzten Variablen kann auf einen Fehler hinweisen, während ungenutzte Imports nur den Kompilierungsprozess verlangsamen. Sammle genug ungenutzte Imports in deinem Codebaum an und die Dinge können sehr langsam werden. Aus diesen Gründen erlaubt Go beides nicht.

57voto

chuacw Punkte 1343

Ich bin vor 2 Jahren darauf gestoßen, als ich Go gelernt habe, also habe ich meine eigene Funktion deklariert.

// UNUSED ermöglicht es, ungenutzte Variablen in Go-Programmen zu inkludieren
func UNUSED(x ...interface{}) {}

Und dann kannst du es so verwenden:

UNUSED(x)
UNUSED(x, y)
UNUSED(x, y, z)

Das Tolle daran ist, du kannst alles an UNUSED übergeben.

Ist das besser als das Folgende?

_, _, _ = x, y, z

Das liegt bei dir.

53voto

lunux2008 Punkte 539

Sie können hierfür eine einfache "Nullfunktion" verwenden, zum Beispiel:

func Use(vals ...interface{}) {
    for _, val := range vals {
        _ = val
    }
}

Die Sie folgendermaßen verwenden können:

package main

func main() {
    a := "deklariert und nicht verwendet"
    b := "eine andere deklariert und nicht verwendet"
    c := 123

    Use(a, b, c)
}

Es gibt auch ein Paket dafür, sodass Sie die Use-Funktion nicht jedes Mal definieren müssen:

import (
  "github.com/lunux2008/xulu"
)

func main() {
  // [..]

  xulu.Use(a, b, c)
}

39voto

Martin Tournoij Punkte 24903

Gemäß dem FAQ:

Einige haben nach einer Compileroption gefragt, um diese Überprüfungen auszuschalten oder zumindest auf Warnungen zu reduzieren. Eine solche Option wurde jedoch nicht hinzugefügt, da Compileroptionen die Semantik der Sprache nicht beeinflussen sollten und weil der Go-Compiler keine Warnungen, sondern nur Fehler ausgibt, die die Kompilierung verhindern.

Es gibt zwei Gründe, warum es keine Warnungen gibt. Erstens, wenn es sich lohnt, sich zu beschweren, lohnt es sich, den Code zu korrigieren. (Und wenn es nicht lohnt, ihn zu korrigieren, ist es nicht erwähnenswert.) Zweitens, das Generieren von Warnungen durch den Compiler ermutigt die Implementierung dazu, vor schwachen Fällen zu warnen, die die Kompilierung lärmig machen können und echte Fehler überdecken, die behoben werden sollten.

Ich stimme dem nicht unbedingt aus verschiedenen Gründen zu, die es nicht wert sind, darauf einzugehen. Es ist wie es ist, und es wird sich in naher Zukunft wahrscheinlich nicht ändern.

Für Pakete gibt es das goimports Tool, das fehlende Pakete automatisch hinzufügt und nicht verwendete entfernt. Zum Beispiel:

# Installieren
$ go get golang.org/x/tools/cmd/goimports

# -w schreibt die Quellcodedatei anstelle von stdout
$ goimports -w my_file.go

Sie sollten dies von einem halbwegs vernünftigen Editor ausführen können, zum Beispiel für Vim:

:!goimports -w %

Die goimports Seite listet einige Befehle für andere Editoren auf, und in der Regel wird sie automatisch ausgeführt, wenn Sie den Puffer auf die Festplatte speichern.

Beachten Sie, dass goimports auch gofmt ausführen wird.


Wie bereits erwähnt, ist der einfachste Weg für Variablen, diese (temporär) _ zuzuweisen:

// Keine Fehler
lecker := "Eiscreme"
grauenvoll := "Marmite"

// Für Debugging auskommentiert
//essen(lecker, grauenvoll)

_, _ = lecker, grauenvoll

13voto

max pleaner Punkte 24865

Im Falle, dass andere Schwierigkeiten haben, dies zu verstehen, denke ich, dass es helfen könnte, es in sehr einfachen Worten zu erklären. Wenn Sie eine Variable haben, die Sie nicht verwenden, zum Beispiel eine Funktion, für die Sie den Aufruf auskommentiert haben (ein häufiger Anwendungsfall):

myFn := func() {}
// myFn()

Sie können eine nutzlose/leere Variable der Funktion zuweisen, damit sie nicht mehr unbenutzt ist:

myFn := func() {}
_ = myFn
// myFn()

CodeJaeger.com

CodeJaeger ist eine Gemeinschaft für Programmierer, die täglich Hilfe erhalten..
Wir haben viele Inhalte, und Sie können auch Ihre eigenen Fragen stellen oder die Fragen anderer Leute lösen.

Powered by:

X