Anzahl der Elemente in einem Kanal

86

Wie messen Sie mithilfe eines gepufferten Kanals, wie viele Elemente sich im Kanal befinden? Zum Beispiel erstelle und sende ich auf einem Kanal wie diesem:

send_ch := make(chan []byte, 100)
// code
send_ch <- msg

Ich möchte messen, wie viele Nachrichten sich im Kanal send_ch befinden .

Ich bin mir bewusst, dass die Messung aufgrund der Parallelität nicht genau ist, da zwischen Messung und Aktion eine Prävention auftreten kann (z. B. in diesem Video beschrieben Google I / O 2012 - Go Concurrency Patterns ). Ich werde dies für die Flusskontrolle zwischen Produzenten und Verbrauchern verwenden, dh sobald ich ein hohes Wasserzeichen passiert habe, und ein Verhalten ändern, bis ich durch ein niedriges Wasserzeichen zurückkehre.

Sonia Hamilton
quelle

Antworten:

150

http://golang.org/pkg/builtin/#len

func len (v Type) int
Die integrierte len-Funktion gibt die Länge von v entsprechend ihrem Typ zurück:

  • Array: Die Anzahl der Elemente in v.
  • Zeiger auf Array: Die Anzahl der Elemente in * v (auch wenn v gleich Null ist).
  • Slice oder Map: die Anzahl der Elemente in v; Wenn v Null ist, ist len ​​(v) Null.
  • Zeichenfolge: Die Anzahl der Bytes in v.
  • Kanal: Die Anzahl der Elemente, die sich im Kanalpuffer in der Warteschlange befinden (ungelesen). Wenn v Null ist, ist len ​​(v) Null.
package main

import "fmt"

func main() {
        c := make(chan int, 100)
        for i := 0; i < 34; i++ {
                c <- 0
        }
        fmt.Println(len(c))
}

wird ausgegeben:

34
Artem Shitov
quelle
4
Danke Artem. Das ist eine unerwartete Verwendung von len - ich hätte erwartet, dass es die Kapazität eines Kanals zurückgibt, nicht die Anzahl der darin enthaltenen Elemente! Gut zu wissen, nochmals vielen Dank.
Sonia Hamilton
39
Wenn Sie die Kapazität gewollt hätten, würde die eingebaute Funktion capdies tun.
ANisus
6
Was ich hier interessant finde, ist, dass wenn der Kanal ohne Kapazität ( c := make(chan int)) erstellt wird, man seine Länge nicht bekommen kann. Ich habe keinen Grund dafür gefunden. Ja, die Kapazität kehrt ebenfalls als 0 zurück
Brettski
Ich fühle mich komisch, dass ich, wenn es ungepuffert ist, seine Länge nicht bekommen kann. Und wenn man Goroutinen benutzt, ist das ein bisschen durcheinander.
Berkant Ipek
5
@Brettski und Berkant, Wenn der Kanal ungepuffert ist (Kapazität = 0), ist die Länge immer Null. Der Sender blockiert, bis der Empfänger den Wert erhalten hat. golang.org/doc/effective_go.html#channels
Farshid T