이들 키워드는 비동기 프로그래밍을 위해 사용되며, 이를 이용해 앱이 무거운 작업을 수행하면서도 UI를 부드럽게 유지할 수 있게 돕습니다.
'async*': 이 키워드는 비동기 제너레이터 메서드를 선언하는 데 사용됩니다. 비동기 제너레이터는 시간이 오래 걸리는 연산이 있을 때 사용되며, 'Stream' 객체를 반환합니다. 'async*' 키워드는 메서드를 비동기적으로 만들며, 여러 반환 값을 가능하게 합니다.
Stream<int> countStream(int to) async* {
for (int i = 1; i <= to; i++) {
await Future.delayed(Duration(seconds: 1));
yield i;
}
}
이 예제에서 'countStream' 함수는 1초 간격으로 숫자를 생성하는 비동기 스트림입니다. 'yield'를 사용하여 각 숫자를 출력합니다.
'yield': 이 키워드는 제너레이터 내에서 사용됩니다. 'yield'를 사용하면 함수의 실행을 일시 중지하고 값을 반환할 수 있습니다. 함수가 다시 호출되면 중지된 위치에서 실행을 재개합니다. 이렇게 하면 함수는 시간이 걸리는 작업을 수행하면서도 값을 계속 생성할 수 있습니다.
위의 예제에서 보듯이, 'yield' 키워드는 각 숫자를 반환하는 데 사용되며, 이 때 함수의 실행이 일시 중지됩니다. 'Future.delayed'가 다시 완료될 때까지입니다. 이후에 다음 숫자가 'yield'에 의해 생성되고, 이 프로세스가 계속 반복됩니다.
이 두 키워드는 Flutter에서 UI를 업데이트하는 동안 시간이 걸리는 작업을 수행해야 할 때 매우 유용합니다. 예를 들어, 네트워크에서 데이터를 가져오는 동안 스피너를 보여주는 등의 작업을 수행할 수 있습니다.
'async'와 'async*' 키워드는 둘 다 비동기 함수를 선언하는 데 사용되지만, 반환하는 객체와 처리 방식에서 차이가 있습니다.
Future<String> fetchData() async {
// 시간이 걸리는 네트워크 요청을 가정합니다.
await Future.delayed(Duration(seconds: 2));
return '데이터';
}
Stream<int> countStream(int to) async* {
for (int i = 1; i <= to; i++) {
await Future.delayed(Duration(seconds: 1));
yield i;
}
}
int add(int a, int b) {
return a + b; // 함수 실행이 여기서 종료되고, 결과를 반환합니다.
}
Iterable<int> count(int to) sync* {
for (int i = 1; i <= to; i++) {
yield i; // 함수의 실행이 여기서 일시적으로 중지되고, i를 반환합니다.
// 다음 호출 때에는 여기서 계속 실행됩니다.
}
}
'yield'는 'return'과 달리 함수를 종료시키지 않고, 여러 값을 시간에 따라 반환할 수 있게 해줍니다. 이러한 특성은 스트림 생성이나 느긋한(lazy) 계산 등에서 매우 유용합니다.