برنامهنویسی ناهمگام یکی از اصول مهم در توسعه نرمافزار است، بهویژه در جاوااسکریپت که بهصورت ذاتی تکنخی (single-threaded) اجرا میشود. با استفاده از الگوهای مختلف برنامهنویسی ناهمگام میتوان به مدیریت بهینه و کارآمد چندین عملیات همزمان پرداخت. در این مقاله به بررسی سه الگوی رایج: Promise.race، Promise.all، و Promise.any میپردازیم و کاربرد هر کدام را در کدنویسی توضیح خواهیم داد.
قبل از اینکه به این الگوها بپردازیم، لازم است بدانیم که یک Promise در جاوااسکریپت، شیئی است که نمایانگر یک عملیات ناهمگام بوده و میتواند یکی از سه حالت زیر را داشته باشد:
Fulfilled: عملیات با موفقیت به پایان رسیده است.
Rejected: عملیات با شکست مواجه شده است.
Pending: عملیات هنوز در حال انجام است و نتیجهای مشخص نشده است.
Promise.all یک الگوی رایج برای اجرای چندین عملیات ناهمگام است که منتظر میماند تا تمامی Promises پاسخی بازگردانند. اگر یکی از Promises با شکست مواجه شود، بقیه هم شکست میخورند.
مثال:
const promise1 = new Promise((resolve) => setTimeout(() => resolve('Result 1'), 2000));
const promise2 = new Promise((resolve) => setTimeout(() => resolve('Result 2'), 3000));
const promise3 = new Promise((resolve, reject) => setTimeout(() => reject('Error in promise 3'), 2500));
Promise.all([promise1, promise2, promise3])
.then((results) => {
console.log(results); // This won't execute
})
.catch((error) => {
console.error(error); // Output: Error in promise 3
});
مزایا:
تمامیت نتایج: تمام Promises باید موفق باشند تا خروجی نهایی بازگردانده شود.
کاربردی برای عملیات وابسته به چند نتیجه: مناسب برای زمانی که نیاز دارید چند عملیات مختلف قبل از ادامه کار انجام شوند.
معایب:
شکنندگی بالا: اگر یک Promise شکست بخورد، کل عملیات شکست میخورد و نتایج دیگر Promises برگردانده نمیشود.
در Promise.race، خروجی بر اساس اولین Promises که به حالت "fulfilled" یا "rejected" برسد، برگردانده میشود. این الگو برای مواقعی مناسب است که تنها نتیجه سریعترین عملیات اهمیت دارد.
مثال:
const promise1 = new Promise((resolve) => setTimeout(() => resolve('Result 1'), 2000));
const promise2 = new Promise((resolve) => setTimeout(() => resolve('Result 2'), 1000));
Promise.race([promise1, promise2])
.then((result) => {
console.log(result); // Output: Result 2
})
.catch((error) => {
console.error(error);
});
مزایا:
سرعت بالا: اولین Promise که نتیجه بدهد، مورد قبول است. برای مثال در مسابقات زمانی (Race Condition) مفید است.
کاربردی در زمانسنجی (Timeout): برای محدود کردن مدت زمان اجرای یک Promise میتوان از آن استفاده کرد.
معایب:
عدم تضمین تمامیت نتایج: ممکن است تنها اولین Promise نتیجه دهد و بقیه Promises نادیده گرفته شوند، حتی اگر آنها شکست بخورند.
Promise.any یک روش جدیدتر در جاوااسکریپت (معرفی شده در ES2021) است که منتظر اولین Promise موفق میماند. در این الگو، برخلاف Promise.race، تنها Promises موفق مهم هستند و در صورت شکست همه Promises، خطا برگردانده میشود.
مثال:
const promise1 = new Promise((resolve, reject) => setTimeout(() => reject('Error in promise 1'), 1000));
const promise2 = new Promise((resolve) => setTimeout(() => resolve('Result 2'), 2000));
const promise3 = new Promise((resolve) => setTimeout(() => resolve('Result 3'), 3000));
Promise.any([promise1, promise2, promise3])
.then((result) => {
console.log(result); // Output: Result 2
})
.catch((error) => {
console.error(error); // This won't execute
});
مزایا:
موفقیت مهم است: اولین Promise موفق مهم است و شکست دیگر Promises تأثیری ندارد.
کاربردی در عملیات ناهمزمان وابسته به اولین موفقیت: زمانی که چند عملیات مختلف در جریان است و موفقیت حداقل یکی از آنها کافی است.
معایب:
نیاز به ES2021 یا بالاتر: برای استفاده از این الگو باید از نسخههای جدیدتر جاوااسکریپت استفاده کنید.
ویژگی |
Promise.any |
Promise.race |
Promise.all |
نتیجه نهایی |
بازگرداندن اولین Promise موفق |
بازگرداندن اولین Promise که نتیجه دهد |
بازگرداندن تمامی نتایج موفق |
خطاها |
تنها در صورت شکست تمامی Promises خطا برگردانده میشود |
تنها خطای اولین Promise برگردانده میشود |
اگر یکی شکست بخورد، کل Promises شکست میخورد |
کاربرد |
زمانی که موفقیت یکی از Promises کافی است |
زمانی که نتیجه سریعترین عملیات مهم است |
زمانی که به تمامی نتایج نیاز است |
هر یک از این الگوهای Promises کاربردهای خاص خود را در برنامهنویسی ناهمگام دارند. برای عملیاتهای موازی که نیاز به تمامی نتایج موفق دارید، از Promise.all استفاده کنید. اگر سرعت مهمترین عامل است، Promise.race گزینه مناسبی است. و اگر تنها موفقیت یکی از عملیاتهای موازی برایتان کافی است، Promise.any میتواند بهترین انتخاب باشد.
نظری یافت نشد
آموزش کامل توابع سازنده (Constructors) و پروتوتایپها (Prototypes) در جاوا اسکریپت: راهنمای جامع
28م مهر 1403
مطالعه بیشتر
آشنایی با Inheritance در CSS: اصول وراثت و مدیریت استایلها
12م آبان 1403
مطالعه بیشتر
استفاده از display در CSS: تغییر نحوه نمایش عناصر - راهنمای جامع
9م آبان 1403
مطالعه بیشتر
آموزش استفاده از cubic-bezier در CSS برای انیمیشنهای سفارشی و حرفهای
12م آبان 1403
مطالعه بیشتر
استفاده از calc در CSS: محاسبات پویا برای طراحیهای منعطف
12م آبان 1403
مطالعه بیشتر
آموزش تگهای متنی اولیه در HTML: استایلدهی و قالببندی متنها
18م مرداد 1402
مطالعه بیشتر
آموزش لیستها در CSS: طراحی و استایلدهی ساده برای لیستهای HTML
10م شهریور 1402
مطالعه بیشتر
مفاهیم پیشرفته اشیاء در جاوا اسکریپت: مدیریت خصوصیات و متدها
4م مهر 1403
مطالعه بیشتر
مقدمهای به template و دیتابایندینگ در Vue.js: نحوه مدیریت دادهها و رندرینگ پویا
28م شهریور 1402
مطالعه بیشتر
آموزش ساخت یک گالری تصویر با استفاده از جاوا اسکریپت: راهنمای گام به گام
3م آبان 1403
مطالعه بیشتر
آموزش ایجاد تصویر و لینک در HTML: نحوه استفاده از تگهای img و a
21م مرداد 1402
مطالعه بیشتر
آموزش کامل ویژگی background در CSS: تنظیمات پسزمینه برای طراحی وب راهنمای جامع
5م شهریور 1402
مطالعه بیشتر
تمامی حقوق معتلق به ناشر سایت است و کپی از آن پیگرد قانونی دارد