0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

【JavaScript】Promiseについて

Last updated at Posted at 2024-11-16

今回はPromiseについての備忘録です。

1:「Promise」とは?

・【非同期処理を、より簡単に書けるようにしたもの】です。

・非同期処理といえばコールバック関数がありますね。
そんなコールバック関数も「チェーン」により処理を繋げることができます。
⬇︎

main.js
//////コールバック関数の「チェーン」の例。

//⬇︎①sleep関数を定義する。
//引数にはcallbackに「コールバック関数function(val)」が渡ってくる。
//setTimeout内で「コールバック関数function(val)」が実行される。
function sleep(callback, val) {
  setTimeout(function() {
    console.log(val++);  //コンソール結果 「0, 1, 2, 3,」と1秒ずつ値が表示される。
    callback(val);
  }, 1000);
}


//⬇︎②sleep関数を実行する。
//「sleep関数の中のコールバック関数(function(val)の中で【更にsleepを呼びます。】」
//これが【複数の非同期処理を順番に実行する、非同期処理のチェーン】です。
sleep(function(val) {
  sleep(function(val) {
    sleep(function(val) {
      sleep(function(val) {
  
      }, val);
    }, val);
  }, val);
}, 0);



⬇︎
❌ここで問題となるのはsleepの中で更にsleepを読み込むため、「多階層が深くなりコードの可読性が下がります。」
⬇︎
❌そのため「コールバック関数というのは、非同期のチェーンを繋げるために適した記述では無い」ことが分かります。
⬇︎
⭕️この問題を解決するために【Promiseという非同期処理のチェーン】を繋げるためのオブジェクトが導入されました。

2: 「Promiseの書き方」

・Promise構文
⬇︎
・new Promise➡︎「Promiseをインスタンス化」してあげます。

・.thenメソッド、.catchメソッド、.finallyメソッドを使って➡︎「非同期処理に対して制御を加えてあげることになります。」

main.js
////Promise構文
new Promise(function(resolve, reject)
 //同期処理が実行される。
).then(
 //非同期処理が実行される。
).catch(
 //非同期処理が実行される。
).finally(
 //非同期処理が実行される。
);

main.js
////⬇︎上記のPromise構文を参考にした具体例。
//多階層にならないのでPromiseは非同期処理のチェーンを処理するために適した記述です。
new Promise(function (resolve) {
  resolve('hello');
}).then(function(data) {
    console.log(data); //コンソール結果➡︎コールスタックが空っぽになった後に、’hello’が出力される。
  })
  .then(function(data) {
    console.log(data); //コンソール結果は同じく’hello'で、しかも多階層にならない!Promiseは非同期処理のチェーンを処理するために適した記述方法!
  })
  .catch(function(data) (
    console.log('エラーだよ'); //catchはエラー処理。
  ).finally(function(){
    console.log('終了') //finallyで終了処理。
  });


■new Promiseの引数として「function(resolve, reject)」を設定します。

・resolveが呼ばれた場合
解決処理が実行される。
「resolve」が呼ばれた場合には【.thenメソッドの中のコールバック関数function(data)が実行されることになり、引数dataにはresolveで渡した実引数'hello'などが渡ってきます。」

・rejectが呼ばれた場合
エラー処理が実行される。
「reject」というのは【Promiseのコールバック関数で、エラーが発生した時にPromiseに通知してあげるために使用する関数】です。

・引数function(data)
resolve(‘hello’)や、reject('bye')で渡した実引数’hello’や'bye'が渡ってきます。

■「then, catch, finally」の各解説。

・thenメソッド
resolveで条件に一致したら実行される。catchメソッドはスキップされて、finallyメソッドに処理が移ります。

・catchメソッド
rejectでエラー処理が実行される。.catchメソッドが完了したら、.finallyメソッドに処理が移ります。

・finallyメソッドが呼ばれた場合
thenメソッド、catchメソッドの後に呼ばれるfinallyメソッドは終了処理を記述していきます。
.finallyメソッドの中で使用するコールバック関数functionは、【(data)引数を取ることができません。

3: 「Promiseの書き方:2」

Promiseのおかげで非同期処理しやすくなったな〜と実感してきた所で、

①「throw new Error」でthenメソッドから➡︎catchのエラー処理を強制実行する。

②「setTimeoutを使った非同期処理の書き方」の紹介。

などの実装をしてみます。(少し見えにくいかもしれませんがご容赦ください…。)

main.js
////①「throw new Error」でthenメソッドから➡︎catchのエラー処理を強制実行する。
new Promise(function (resolve, reject) {
  console.log('promise 開始');
  resolve('hello'); //⬅︎resolveでthenを実行する。
  //reject('bye');
})
  .then(function (data) {
    console.log('then①:' + data); //⬅︎コンソール結果:then①:hello
    throw new Error(); //⬅ここでthrow new Errorを使うと「catchの処理が強制実行します。」
    return data; //⬅return dataを設定すると「次の処理にdata(resolveやrejectの引数hello)を渡せる。
    //throw new Error();をコメントアウトするとhelloを渡せる。
  })
  .then(function (data) { 
   //このthenメソッドは無視されcatchに処理が移る。
    console.log('then②:' + data);
    return data;
  })
  .catch(function (data) {
     console.log('エラーcatch:' + data); //⬅︎コンソール結果:エラーcatch
  })
  .finally(function () {
    console.log('finally'); //⬅︎最後にfinallyで終了。
  });

console.log('global end 終了'); //同期的に処理されるので「コンソールのpromise開始のあとに出ます。」


main.js
////②「setTimeoutを使った非同期処理の書き方」の紹介。
new Promise(function (resolve, reject) {
  console.log('promise 開始');
  //⬇︎setTimeoutを実行。1秒後にresolveでthenメソッドを処理していく。
  setTimeout(function () {
    resolve('hello');
  }, 1000);
  //reject('bye');
})
  .then(function (data) {
    console.log('then①:' + data); //コンソール結果: then①:hello
    return data;
  })
  .then(function (data) {
    console.log('then②:' + data); //コンソール結果: then②:hello
    return data;
  })
  .catch(function (data) {
    //このcatchメソッドは今回はもちろん実行されない。
    // console.log('catch:' + data);
  })
  .finally(function () {
    console.log('finally'); //⬅︎最後にfinallyで終了。
  });

console.log('global end 終了'); //同期的に処理されるので「コンソールのpromise開始のあとに出ます。」


⭕️Promiseのおかげで「コールバック関数などの非同期処理を、見やすく書けるようになります。」


4:「Promise」の備忘録でした

こうしてインプットとアウトプットを繰り返していると、記憶に定着して1歩ずつ進んでいるなと感じます。

0
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?