Вы не можете сделать это для sync*
функций.
Единственный способ, которым Iterable
может сообщить об ошибке, - это вызвать метод Iterator
'moveNext
.Чтобы сделать это, метод sync*
должен бросить.Когда функция sync*
выдает, она завершает тело функции, что делает невозможным продолжение этого тела и получение большего количества значений.
То же самое происходит с async*
функциями, которые выдают, ноу вас также есть другой способ выдать ошибку.Так как поток может сообщать об ошибках как часть потока, возможно выдавать ошибки и продолжать, вы просто не можете сделать это путем выброса .
Stream<double> generateRandomNumbers([int seed]) async* {
final random = Random(seed);
while (true) {
final nextDouble = random.nextDouble();
if (nextDouble > 0.8) {
yield* Future<double>.error(Exception('$nextDouble')).asStream();
continue;
}
yield nextDouble;
}
}
Хитрость заключается в том, чтобыyield*
поток, который содержит ошибку.Вы можете сделать это разными способами.
yield* Future<double>.error(theError).asStream();
или
yield* () async* { throw theError; } ();
или
yield* (StreamController<double>()..addError(theError)..close()).stream;
До тех пор, пока класс Stream
не получит Stream.error
cosntructor, будущее как поток - самый простой и читаемый подход.