Ответ
Future<T> — это объект, представляющий результат потенциально асинхронной операции, которая завершится либо успешным значением типа T, либо ошибкой. Это основа работы с асинхронным кодом в Dart (сетевыми запросами, чтением файлов, таймерами).
Состояния Future:
- Незавершенный (Uncompleted): Операция еще выполняется.
- Завершенный с значением (Completed with a value): Операция успешно завершилась.
- Завершенный с ошибкой (Completed with an error): Операция завершилась неудачно.
Основные способы работы с Future:
- Использование
async/await(рекомендуется для линейного кода):
Future<String> fetchUserData() async {
// Имитация сетевого запроса
await Future.delayed(Duration(seconds: 1));
// В реальности здесь будет, например, http.get()
return '{"name": "John"}';
}
void main() async {
try {
print('Загрузка...');
String jsonData = await fetchUserData(); // Код "ждет" завершения Future
print('Данные получены: $jsonData');
} catch (error) {
print('Ошибка загрузки: $error');
}
}
- Использование цепочек
then/catchError/whenComplete:
void main() {
fetchUserData()
.then((data) {
print('Данные получены: $data');
return data.length; // Можно преобразовать результат
})
.then((length) => print('Длина данных: $length'))
.catchError((error) => print('Ошибка: $error'))
.whenComplete(() => print('Операция завершена (успех или ошибка).'));
}
Ключевой момент: Future не блокирует основной поток выполнения. Код после вызова асинхронной функции продолжает выполняться сразу, а результат обрабатывается, когда Future завершится.
Ответ 18+ 🔞
Давай разберёмся с этим Future<T>, а то у меня терпения ноль ебать, когда люди его не понимают. Представь, что ты отправил заказ в интернет-магазин. Ты не стоишь у почтового ящика, упершись лбом в стену, пока посылка едет. Ты живёшь своей жизнью, а когда курьер звонит в дверь — получаешь результат. Вот Future — это и есть твоя посылка, которая ещё в пути.
Это объект, который обещает: «Чувак, я тебе принесу либо результат типа T (например, строку с данными), либо ошибку, если всё накрылось медным тазом». И у него три состояния, проще некуда:
- Незавершённый (Uncompleted): Посылка где-то на сортировочном центре, операция выполняется.
- Завершённый с значением (Completed with a value): Ура! Курьер принёс коробку. Всё внутри целое.
- Завершённый с ошибкой (Completed with an error): А вот тут пидарас шерстяной, посылку потеряли или она пришла разбитой. Всё, пиздец.
Как с этим работать, чтобы не сойти с ума?
- Способ первый, нормальный (
async/await): Самый читаемый, почти как обычный код. Просто пишешьasyncперед функцией иawaitперед тем, что нужно «подождать».
Future<String> fetchUserData() async {
// Представь, что это сетевой запрос, а не просто задержка
await Future.delayed(Duration(seconds: 1)); // Имитируем ожидание
return '{"name": "John"}'; // Вот твой успешный результат
}
void main() async {
try {
print('Загрузка...');
// Код тут как бы "приостанавливается", пока Future не выполнится,
// но основной поток приложения не блокируется! Это важно.
String jsonData = await fetchUserData();
print('Данные получены: $jsonData'); // А вот и результат
} catch (error) {
// Если что-то пошло не так — летим сюда
print('Ошибка загрузки: $error');
}
}
- Способ второй, классический (
then/catchError): Более старый, но иногда полезный. Построение цепочек.
void main() {
fetchUserData()
.then((data) {
print('Данные получены: $data');
return data.length; // Можешь что-то преобразовать и передать дальше
})
.then((length) => print('Длина данных: $length')) // Принял результат прошлого then
.catchError((error) => print('Ошибка: $error')) // Ловим всё, что упало
.whenComplete(() => print('Операция завершена (успех или ошибка).')); // Выполнится в любом случае, типа finally
}
Самый важный момент, который все тупят: Когда ты вызываешь функцию, которая возвращает Future, основной поток НЕ БЛОКИРУЕТСЯ. Он сразу идёт выполнять следующий код, а твой Future тихо себе работает где-то на фоне. Потом, когда он готов, он либо вызывает твой колбэк в then, либо «разрешает» твой await. Если этого не понять, будешь сидеть и охуевать, почему интерфейс не виснет при загрузке данных. Вот и вся магия, ебать копать.