Générateur de type "tail -f" dans Go
La tâche consiste à créer une fonction similaire au "tail -f" de Python qui fournit un flux continu de lignes à partir d'un fichier au fur et à mesure de leur écriture, sans bloquer le thread principal.
Solution originale
Le code Go fourni utilise une goroutine asynchrone pour constamment surveiller le fichier à la recherche de nouvelles lignes, ce qui soulève des inquiétudes quant au style Go idiomatique et à une complexité excessive potentielle.
Approche plus propre
Une approche Go plus simple et idiomatique consiste à créer un wrapper autour le lecteur de fichiers qui se met en veille uniquement lorsqu'il atteint la fin du fichier :
<code class="go">type tailReader struct { io.ReadCloser } func (t tailReader) Read(b []byte) (int, error) { for { n, err := t.ReadCloser.Read(b) if n > 0 { return n, nil } else if err != io.EOF { return n, err } time.Sleep(10 * time.Millisecond) } }</code>
Utilisation
Ce wrapper peut être utilisé partout où un io.Reader standard est attendu. Par exemple, pour parcourir des lignes à l'aide de bufio.Scanner :
<code class="go">t, err := newTailReader("somefile") if err != nil { log.Fatal(err) } defer t.Close() scanner := bufio.NewScanner(t) for scanner.Scan() { fmt.Println(scanner.Text()) }</code>
Alternativement, le lecteur peut être utilisé pour des tâches plus complexes, telles que la gestion des valeurs JSON ajoutées :
<code class="go">t, err := newTailReader("somefile") if err != nil { log.Fatal(err) } defer t.Close() dec := json.NewDecoder(t) for { var v SomeType if err := dec.Decode(&v); err != nil { log.Fatal(err) } fmt.Println("the value is ", v) }</code>
Avantages
Cette approche offre plusieurs avantages :
Ce qui précède est le contenu détaillé de. pour plus d'informations, suivez d'autres articles connexes sur le site Web de PHP en chinois!