Go TCP-Lesevorgänge sind nicht blockierend: Adressierung unvollständiger Datenempfang
In Go sind TCP-Lesevorgänge nicht blockierend, was bedeutet, dass sie sofort zurückgegeben werden mit allen verfügbaren Daten, auch wenn diese geringer sind als erwartet. Dieses Verhalten unterscheidet sich von den blockierenden Lesevorgängen von C, die warten, bis die erforderliche Datenmenge empfangen wurde.
Grund für nicht blockierenden Lesevorgang
TCP arbeitet als Bytestrom , die während der Übertragung fragmentiert werden kann. Daher ist es unmöglich, das Ende einer Nachricht allein anhand der Anzahl der empfangenen Bytes zu bestimmen. Dies erfordert benutzerdefinierte Trennzeichen oder andere Mechanismen, um Nachrichtengrenzen zu bestimmen.
Lösung für unvollständige Daten
Um eine bestimmte Anzahl von Bytes zu lesen, verwenden Sie io.ReadAtLeast oder io.ReadFull . Führen Sie für beliebige Bedingungen eine Schleife im Read-Aufruf durch, bis kein Fehler mehr vorliegt oder die angegebene Bedingung erfüllt ist.
Beispiel:
<code class="go">package main import ( "fmt" "net" "time" ) func main() { conn, _ := net.Dial("tcp", "127.0.0.1:4243") // Set a deadline to prevent hanging reads _ = conn.SetReadDeadline(time.Now().Add(10 * time.Second)) // Loop to read until a newline is encountered for { buf := make([]byte, 512) n, err := conn.Read(buf) if err != nil { fmt.Println(err) break } if n > 0 { str := string(buf[:n]) if str[len(str)-1] == '\n' { fmt.Println(str) break } } } }</code>
Andere Überlegungen
Das obige ist der detaillierte Inhalt vonWie gehe ich mit unvollständigem Datenempfang bei nicht blockierenden TCP-Lesevorgängen von Go um?. Für weitere Informationen folgen Sie bitte anderen verwandten Artikeln auf der PHP chinesischen Website!