요즈음은 비동기 프로그래밍이 기본이다.
다트에서 비동기에 관련된 핵심 클래스는 Future 와 Stream 이며, async 와 await 키워드와 함께 사용한다.
다트 코드는 단일 쓰레드에서 실행된다.
Future 클래스
비동기 함수는 Future 클래스를 리턴한다. 이 Future 클래스는 미래에 비동기 작업이 끝나면 값을 받아오는 클래스이다
Future클래스에는 콜백을 2개 등록할 수 있다.
- 비동기 함수가 성공시 성공에 대한 콜백
- 비동기 함수가 error가 발생 시 exception을 일으키는 콜백
Future는 두가지의 state를 가진다.
- Uncompleted, 비동기 함수가 아직 끝나지 않은 상태
- Completed, 비동기 함수가 작업이 끝난 상태. 성공하면 value를, 실패하면 error 값을 가져온다
Future<T>는 비동기 처리가 성공시 T타입의 값을 가져온다. 만약 T가 String이면 Future<String> 으로 적어준다.
값을 리턴하지 않을 경우 Future<void> 라고 적는다.
void main(){
print('Before the Future');
Future((){
print('Running the Future');
}).then((_) => print('Future is complete.') );
print('After the Future');
/*
1. 다트에 의해서 future 객체가 내부적인 배열에 등록
2. Future 관련해서 실행되어야 하는 코드들이 이벤트 Queue 에 등록
3. 불완전한 future 객체 반환
4. Synchronous 방식으로 실행되어야 할 코드 먼저 실행
5. 최종적으로 실제적인 data 값이 future 객체로 전달
*/
/* 실행 결과
Before the Future
After the Future
Running the Future
Future is complete.
*/
}
|
Future의 then(), catchError() 함수
then() 함수를 통해 Future가 complete 되면 실행해줄 콜백을 등록할 수 있다.
또한 catchError() 함수를 통해 에러처리를 해줄 수 있다.
String createOrderMessage(){
var order = fetchUserOrder();
return 'Your order is : ${order}';
}
Future<String> fetchUserOrder(){
return Future.delayed(
Duration(seconds: 2),
() => 'Large Latte',
);
}
void main(){
print('Fetching user order...');
print(createOrderMessage());
}
/* 실행결과
Fetching user order...
Your order is : Instance of 'Future<String>'
*/
|
원하지 않은 결과가 출력되었다.
async : async 함수 본문 앞에 키워드를 사용하여 비동기로 표시할 수 있다.
async function : async 함수는 async 키워드로 표시된 함수다.
await : await 키워드를 사용하여 비동기식의 완성된 결과를 얻을 수 있다.
await 키워드는 단지 async 내에서 작동하는 기능이다.
Async method
- 메소드를 통해 나오는 결과물은 Future
- await 키워드를 만날 때까지 synchronous 방식으로 코드 처리
- await 키워드를 만나면 future 가 완료될 때까지 대기
- future 가 완료되자마자 그 다음 코드들을 실행
코드를 아래와 같이 수정한다.
future가 완료될 때까지 일시 중단하려면 async 함수에서 await를 사용하면 된다.
Future<String> createOrderMessage() async {
print('synchronous');
var order = await fetchUserOrder();
return 'Your order is : ${order}';
}
Future<String> fetchUserOrder(){
return Future.delayed(
Duration(seconds: 2),
() => 'Large Latte',
);
}
void main() async {
print('Fetching user order...');
print(await createOrderMessage());
}
/* 실행 결과
Fetching user order...
synchronous
Your order is : Large Latte
*/
|
이제 원하는 결과가 출력되었다.
void main() async {
methodA();
await methodB();
await methodC("main");
methodD();
}
void methodA() {
print('A method run.');
}
methodB() async {
print('B method start.');
await methodC('B');
print('B method end.');
}
methodC(String s) {
print('C method start FROM ${s}');
Future(() => print('C Future running FROM ${s}'))
.then((_) => print('C Future is complete FROM ${s}'));
print('C method end FROM ${s}');
}
void methodD() {
print('D method run.');
}
/* 실행결과
A method run.
B method start.
C method start FROM B
C method end FROM B
B method end.
C method start FROM main
C method end FROM main
D method run.
C Future running FROM B
C Future is complete FROM B
C Future running FROM main
C Future is complete FROM main
*/
|
'Flutter 앱 > Dart 언어' 카테고리의 다른 글
Dart Collection (0) | 2022.06.28 |
---|---|
Dart Class(클래스) (0) | 2022.06.27 |
Dart function(함수) (0) | 2022.06.22 |
Dart Type 검사(is, is!) (0) | 2022.06.22 |
Dart const, final (0) | 2022.06.22 |