File.openRead în Dart

Deschide fișierul ca flux de octeți citit pe bucăți; potrivit pentru fișiere mari, rând cu rând.

Sintaxă
Stream<List<int>> openRead([int? start, int? end])

Ce face File.openRead

openRead() nu încarcă tot fișierul în memorie, ci returnează un Stream<List<int>>: fișierul este citit pe bucăți (de obicei de 64 KB). Așa poți prelucra fișiere de câțiva GB cu memorie puțină.

Pentru text, transformi fluxul: .transform(utf8.decoder) dă bucăți de text, apoi .transform(const LineSplitter()) dă rândurile unul câte unul. Le parcurgi cu await for.

Opțional, start și end citesc doar o porțiune: de la octetul start (inclusiv) până la end (exclusiv). Fișierul este deschis abia când începi să asculți fluxul și se închide singur la final.

Parametri

Parametru Descriere
start Opțional. Primul octet citit.
end Opțional. Octetul la care se oprește citirea (exclusiv).

Ce returnează

Un Stream<List<int>> cu bucățile de octeți.

Exemple

Exemplul 1: Citire rând cu rând

import 'dart:convert';
import 'dart:io';

Future<void> main() async {
  await File('jurnal.log').writeAsString('INFO pornire\nEROARE disc plin\nINFO oprire\nEROARE rețea\n');

  var erori = 0;
  final randuri = File('jurnal.log').openRead().transform(utf8.decoder).transform(const LineSplitter());
  await for (final rand in randuri) {
    if (rand.startsWith('EROARE')) {
      erori++;
      print(rand);
    }
  }
  print('Total erori: $erori');
}

Rezultat

EROARE disc plin
EROARE rețea
Total erori: 2

Exemplul 2: Doar o porțiune din fișier

import 'dart:io';

Future<void> main() async {
  await File('alfabet.txt').writeAsString('ABCDEFGHIJ');
  final bucati = await File('alfabet.txt').openRead(2, 6).toList();
  print(bucati);
  print(String.fromCharCodes(bucati.expand((b) => b)));
}

Rezultat

[[67, 68, 69, 70]]
CDEF

Greșeli frecvente

  • Uiți await în fața lui for: un Stream se parcurge cu await for, iar funcția trebuie să fie async.
  • Decodezi fiecare bucată separat cu utf8.decode. Un caracter cu diacritice tăiat între bucăți dă eroare; folosește transform(utf8.decoder).

Comenzi înrudite

  • File.readAsLines: Citește un fișier text și returnează lista rândurilor, fără caracterele de sfârșit de rând.
  • utf8.decoder: Convertoarele din spatele lui utf8: decoder transformă fluxuri de octeți în text, encoder face invers.
  • LineSplitter: Împarte un text în rânduri, recunoscând \n, \r\n și \r; funcționează și pe fluxuri cu transform.
  • File.openWrite: Deschide fișierul pentru scriere și returnează un IOSink în care scrii pe bucăți; trebuie închis cu close().