3つの関数があり、次々に呼び出したい
openTryFunction(){
// function one
this.functionOne();
// after function one
this.functionTwo();
// after function two
this.functionTree(); }
したがって、3つの関数functionOne
、functionTwo
、およびfunctionThree
があります。これらの機能のいずれかが同期か非同期かを示す複数のPnCが存在する場合があります。
これらのシナリオを2つの主要なカテゴリに一般化します。
すべてが同期的です:この場合、コードは次々に(同期的に)実行されます。
関数のいずれかが非同期である場合:この場合、非同期の関数は、呼び出されることになっている関数を許可する必要がありますその後、それが終了したことを知るために。この場合、その非同期関数からPromise/Observableを返すことができます。または、非同期関数の実行が終了した後に呼び出されるコールバック関数を渡すことができます。
これの2つの例は次のとおりです。
次に、次のように記述します。
openTryFunction() {
this.functionOne()
.subscribe(
() => this.functionTwo()
.subscribe(() => this.functionThree()
.subscribe(() => console.log('Function three terminated')))
);
}
functionOne
とfunctionTwo
がプロミスを返す場合、次のようになります。openTryFunction() {
this.functionOne().then(() => {
this.functionTwo().then(() => this.functionThree());
});
}
更新:
async
とawait
を使用して、よりクリーンなコードにすることもできます。同じものの簡単で具体的な例を次に示します。
import { Component } from '@angular/core';
import { HttpClient } from '@angular/common/http';
@Component({
selector: 'my-app',
templateUrl: './app.component.html',
styleUrls: [ './app.component.css' ]
})
export class AppComponent {
name = 'Angular';
users;
constructor(private http: HttpClient) {}
ngOnInit() {
this.getAllData();
}
getUsers() {
return this.http.get('https://jsonplaceholder.typicode.com/users')
.toPromise();
}
getUserPosts(userId) {
return this.http.get(`https://jsonplaceholder.typicode.com/posts?userId=${userId}`)
.toPromise();
}
getPostComments(postId) {
return this.http.get(`https://jsonplaceholder.typicode.com/comments?postId=${postId}`)
.toPromise();
}
async getAllData() {
const users = await this.getUsers();
const posts = await this.getUserPosts(users[0].id);
const comments = await this.getPostComments(posts[0].id);
console.log(users);
console.log(posts);
console.log(comments);
}
}
これは StackBlitz と同じです。
それが理にかなっていることを願っています。
Promiseを使用できます:
functionOne(): Promise<any> {
return Promise.resolve((() => {
// code here
return 'from first'; // return whatever you want not neccessory
})());
}
functionTwo(): Promise<any> {
return Promise.resolve((() => {
// code here
return 'from second'; // return whatever you want not neccessory
})());
}
functionThree() {
// code here
}
this.functionOne().then(data1 => {
console.log(data1);
this.functionTwo().then(data2 => {
console.log(data2);
this.functionThree();
});
});
関数が同期している場合、実行していることは問題ありません。それらが非同期であり、Promiseを返す場合、それらを次のように連結できます。
fOne()
.then(() => {
fTwo()
} ).then(() => {
fThree()
});
または、非同期待機を使用できます。
async function tasks() {
await fOne();
await fTwo();
await fThree();
}
必ず例外を処理するためにcatchを試してください。
関数がオブザーバブルを返す場合、concatMapはあなたの友達です。
fOne()
.concatMap(() => fTwo())
.concatMap(() => fThree());
最後の関数がpromiseを返さない場合、async awaitを使用すると仮定して、最後の呼び出しでawaitを省略できます。
各関数がObservable
を返し、実行シーケンスがconcat
関数によって制御されるこの例を見てください。
export class AppComponent implements OnInit {
name = 'Angular';
values = [];
first(): Observable<string> {
return of('first');
}
second(): Observable<string> {
return of('second');
}
afterSecond(): Observable<string> {
return of('secondish');
}
third(): Observable<string> {
return of('third');
}
ngOnInit() {
let sequence = concat([
this.first,
this.second,
this.afterSecond,
this.third]);
sequence.subscribe(currentFunction => {
currentFunction().subscribe(value => {
this.values.Push(value);
})
});
}
}
リストに追加する関数のconcat
を作成するObservable
関数が好きです。
この呼び出しsequence.subscribe(currentFunction
currentFunction
の各値は関数になります。実際の値を取得するには、Observable
であるため、サブスクライブする必要があります。
完全な例をご覧ください: https://stackblitz.com/edit/angular-functions-in-sequence?file=src%2Fapp%2Fapp.component.ts
これを試すことができます
openTryFunction(){
this.functionOne().then(()=>{this.functionTwo().then(() => {this.functionTree()})})}
機能3は2が完了すると実行され、1が完了すると2が実行されます。
関数がオブザーバブルを返す場合、単純にsubscribe
の次の関数を呼び出します。それ以外の場合は、各関数からプロミスを返します。次に、呼び出された関数をチェーンできます。
functionOne() {
return new Promise((resolve) => {
//
// Your function implementation
//
// Resolve the promise at the end
resolve();
});
}
functionTwo() {
return new Promise((resolve) => {
//
// Your function implementation
//
// Resolve the promise at the end
resolve();
});
}
functionThree() {
return new Promise((resolve) => {
//
// Your function implementation
//
// Resolve the promise at the end
resolve();
});
}
openTryFunction(){
// function one
this.functionOne().then(() => {
// after function one
this.functionTwo().then(() => {
// after function two
this.functionTree();
});
});
}