برنامه نویسی

روش setTimeout جاوا اسکریپت – همه آنچه که باید بدانید

Summarize this content to 400 words in Persian Lang

مقدمه

جاوا اسکریپت یک زبان برنامه نویسی قدرتمند است که به توسعه دهندگان اجازه می دهد تا برنامه های وب پویا و تعاملی ایجاد کنند. یکی از ویژگی های مهم جاوا اسکریپت تابع متد Javascript setTimeout است که انتظار جاوا اسکریپت را فعال می کند.

درک نحوه استفاده موثر setTimeout برای کنترل زمان و جریان برنامه های جاوا اسکریپت شما بسیار مهم است. در این راهنمای جامع، عمیقاً به دنیای جاوا اسکریپت خواهیم پرداخت setTimeout روش و کارکردهای مختلف آن را بررسی کنید.

چه مبتدی یا یک توسعه دهنده با تجربه باشید، این مقاله تمام دانشی را که برای استفاده از پتانسیل کامل نیاز دارید در اختیار شما قرار می دهد. setTimeout در پروژه های جاوا اسکریپت شما

بنابراین، برای تسلط بر هنر زمان‌بندی در جاوا اسکریپت آماده شوید و امکانات جدیدی را برای ایجاد برنامه‌های کاربردی وب پاسخگو و کارآمد باز کنید.

بیایید به دنیای کاوش کنیم setTimeout و تمام اسرار آن را کشف کنید!

پیش نیازها

قبل از کاوش در دنیای setTimeout، داشتن درک اولیه از جاوا اسکریپت و مفاهیم اساسی آن مفید است. آشنایی با متغیرها، توابع و جریان اصلی کنترل (مانند دستورات if و حلقه ها) درک مفاهیم مورد بحث در این مقاله را آسان تر می کند.

اگر به تازگی با جاوا اسکریپت آشنا شده اید یا به یک تجدید کننده نیاز دارید، منابع آنلاین متعددی برای یادگیری اصول اولیه وجود دارد. وب‌سایت‌هایی مانند MDN Web Docs، W3Schools و freeCodeCamp آموزش‌ها و راهنماهای جامعی را ارائه می‌دهند که می‌تواند به شما در شروع سفر جاوا اسکریپت کمک کند.

علاوه بر این، من دو کتاب زیر را برای مبتدیان در جاوا اسکریپت به شدت توصیه می کنم:

برنامه نویسی Head First JavaScript: راهنمای مناسب برای مغز

جاوا اسکریپت: راهنمای قطعی: بر پرکاربردترین زبان برنامه نویسی جهان مسلط شوید

(و بله من آنها را رایگان ارائه می کنم)

با غواصی در این منابع، پایه محکمی در برنامه نویسی جاوا اسکریپت به دست خواهید آورد و شما را به دانش لازم برای کشف پیچیدگی های setTimeout و باز کردن امکانات جدید در پروژه های توسعه وب خود مجهز می کند.

بنابراین، قبل از اینکه به پیچیدگی های آن بپردازیم setTimeout، مطمئن شوید که یک پایه محکم در برنامه نویسی جاوا اسکریپت دارید.

وقتی آماده شدید، بیایید قدرت آن را بررسی کنیم setTimeout و امکانات جدید را در پروژه های توسعه وب خود باز کنید.

هدف از setTimeout

برای شروع، بیایید هدف را درک کنیم setTimeout اول

setTimeout معمولاً در سناریوهایی استفاده می‌شود که می‌خواهید تاخیرها، برنامه‌ریزی رویدادها یا انجام وظایف را در بازه‌های زمانی مشخص انجام دهید.

کمی گیج کننده درست است؟

بیایید با یک مثال این را بفهمیم:

توجه: لطفاً فعلاً در مورد نحو آن فکر نکنید. بعداً در مورد Syntex بحث خواهیم کرد.

فرض کنید می خواهید یک تابع را اعلام کنید اما به جای فراخوانی فوری آن، می خواهید آن را پس از مدت زمان مشخصی فراخوانی کنید.

اینجاست که setTimeout وارد تصویر می شود این قابلیت را برای به تاخیر انداختن اجرای یک تابع فراهم می کند.

به کد زیر دقت کنید:

function greetUser() {
console.log(‘Hello, user!’)
}
setTimeout(greetUser, 1000)

وارد حالت تمام صفحه شوید

از حالت تمام صفحه خارج شوید

در این مثال تابعی به نام داریم greetUser که به سادگی یک پیام تبریک را به کنسول ثبت می کند. می خواهیم اجرای این تابع را 1 ثانیه به تاخیر بیندازیم.

برای رسیدن به این هدف، از setTimeout عملکرد و عبور از greetUser تابع به عنوان آرگومان اول و 1000 به عنوان آرگومان دوم.

و بس!

هنگامی که این کد را اجرا می کنید، جاوا اسکریپت 1 ثانیه منتظر می ماند و سپس پیام تبریک “Hello, user!” به کنسول

نحو و پارامترهای ** setTimeout**

برای استفاده موثر setTimeout، درک نحو و پارامترهای آن مهم است.

نحو اساسی از setTimeout به شرح زیر است:

setTimeout(function, delay, param1, param2, …);

وارد حالت تمام صفحه شوید

از حالت تمام صفحه خارج شوید

بیایید اجزای مختلف را تجزیه کنیم:

اولین پارامتر تابع یا قطعه کدی است که می خواهید پس از تاخیر مشخص شده اجرا کنید. این می تواند یک تابع با نام یا یک تابع ناشناس باشد.

تاخیر پارامتر دوم نشان دهنده فاصله زمانی بر حسب میلی ثانیه قبل از شروع اجرای کد است. مدت زمان تأخیر را قبل از فراخوانی تابع مشخص شده تعیین می کند.

پارامترهای اضافی مانند param1، param2 و غیره اختیاری هستند. می توانید از آنها برای ارسال آرگومان ها به تابع مشخص شده در پارامتر اول استفاده کنید.

اینها setTimeout پارامترها به شما این امکان را می دهند که رفتار تابع را هنگام اجرا سفارشی کنید.

این setTimeout() **یک **timeoutID را برمی گرداند که یک عدد صحیح مثبت است که تایمر ایجاد شده در نتیجه فراخوانی متد را شناسایی می کند. این شناسه زمان پایان می توان از آن برای لغو مهلت با ارسال آن به clearTimeout() روشی که در مقاله ای دیگر به آن خواهیم پرداخت.

توجه: اگر نحو را گیج کننده می بینید، نگران نباشید!

در بخش‌های آینده این وبلاگ، نمونه‌های مختلف و موارد استفاده برای هر پارامتر را با جزئیات بررسی خواهیم کرد. من به شما اطمینان می دهم که با خواندن مقاله کامل، درک واضحی از نحوه استفاده به دست خواهید آورد setTimeout به طور موثر

بنابراین، صبور باشید و به خواندن ادامه دهید تا پتانسیل کامل این عملکرد قدرتمند جاوا اسکریپت را باز کنید.

تجزیه کد setTimeout

من می دانم که شما قبلاً متوجه شده اید که چه اتفاقی برای کدی که قبلاً استفاده می کردیم، افتاده است. اما برای تقویت درک خود، بیایید کد را با هم بشکنیم:

function greetUser() {
console.log(‘Hello, user!’)
}

setTimeout(greetUser, 1000)

وارد حالت تمام صفحه شوید

از حالت تمام صفحه خارج شوید

در این قطعه کد:

ما یک تابع به نام تعریف می کنیم greetUser با استفاده از کلمه کلیدی تابع این تابع وظیفه چاپ پیام تبریک به کنسول را بر عهده دارد.
ما استفاده می کنیم setTimeout تابع زمانبندی اجرای greetUser عملکرد پس از یک تاخیر مشخص تاخیر روی 1000 میلی ثانیه تنظیم شده است که معادل 1 ثانیه است.
اولین استدلال به تصویب رسید setTimeout مرجع تابع است greetUser. این می گوید setTimeout کدام تابع را پس از تأخیر مشخص شده اجرا کنید.
آرگومان دوم 1000 نشان دهنده تاخیر در میلی ثانیه است. دوره زمانی قبل از شروع اجرای کد را تعیین می کند.

با استفاده از setTimeout، به جاوا اسکریپت دستور می دهیم 1 ثانیه صبر کنید و سپس آن را فراخوانی می کنیم greetUser تابع در نتیجه پیام تبریک “سلام کاربر!” روی کنسول چاپ خواهد شد.

استفاده از تابع ناشناس به عنوان پاسخ تماس

در مثال کد قبلی، از یک تابع با نام به عنوان تابع callback در کد استفاده کردیم setTimeout تابع

با این حال، setTimeout همچنین به شما این امکان را می دهد که یک تابع ناشناس را به عنوان یک فراخوان ارائه کنید که پس از تاخیر مشخص شده اجرا می شود.

توابع ناشناس معمولاً زمانی استفاده می شوند که کدی که باید اجرا شود ساده است و نیازی به یک تابع نام جداگانه ندارد.

در اینجا یک مثال است:

setTimeout(function () {
console.log(‘This code executes after the delay’)
}, 1000)

وارد حالت تمام صفحه شوید

از حالت تمام صفحه خارج شوید

در این مورد، تابع ناشناس به عنوان پاسخ به تماس عمل می کند. پس از 1000 میلی ثانیه (یا 1 ثانیه) یک پیام را به کنسول ثبت می کند.

می توانید جایگزین کنید console.log عبارت با هر کدی که می خواهید بعد از تاخیر اجرا کنید. استفاده از توابع ناشناس به عنوان تماس در setTimeout انعطاف پذیری را فراهم می کند و به شما امکان می دهد بدون نیاز به اعلان عملکرد جداگانه، کد را به صورت درون خطی تعریف و اجرا کنید.

ارسال آرگومان ها به تابع callback

در setTimeout تابع callback، شما به راحتی می توانید پارامترها یا آرگومان ها را ارسال کنید.

فرض کنید تابعی دارید که پارامترها را می‌پذیرد و می‌خواهید زمانی که تابع پس از تأخیر اجرا می‌شود، مقادیر خاصی برای آن پارامترها ارائه دهید:

function greet(name) {
console.log(‘Hello, ‘ + name + ‘!’)
}

setTimeout(greet, 5000, ‘John’)

وارد حالت تمام صفحه شوید

از حالت تمام صفحه خارج شوید

در این مثال، تابع greet برنامه ریزی شده است که 5 ثانیه (5000 میلی ثانیه) صبر کند و آرگومان جان به عنوان پارامتر نام ارسال می شود.

شما می توانید تاخیر و مقادیر آرگومان را با توجه به مورد خاص خود تنظیم کنید.

با استفاده از این رویکرد، می‌توانید رفتار تابع callback را با ارسال مقادیر مختلف به عنوان آرگومان سفارشی کنید و امکان اجرای کد پویا و انعطاف‌پذیرتر را فراهم کنید.

در اینجا چند نکته اضافی برای ارسال آرگومان ها به تابع callback آورده شده است:

شما می توانید هر تعداد آرگومان را به تابع callback ارسال کنید.
آرگومان ها به همان ترتیبی که به آن ارسال شدند به تابع callback ارسال می شوند setTimeout.
اگر تعداد متغیری از آرگومان ها را به تابع callback ارسال کنید، می توانید از شی آرگومان ها برای دسترسی به آنها استفاده کنید.

در زیر مثالی آورده شده است:

function processArgs() {
for (let i = 0; i < arguments.length; i++) {
console.log(“Argument ” + (i + 1) + “: ” + arguments[i]);
}
}

setTimeout(processArgs, 1000, “apple”, “banana”, “cherry”);

وارد حالت تمام صفحه شوید

از حالت تمام صفحه خارج شوید

در این مثال، processArgs تابع هر آرگومان را به همراه شاخص مربوط به آن در کنسول چاپ می کند. خروجی خواهد بود:

Argument 1: apple
Argument 2: banana
Argument 3: cherry

وارد حالت تمام صفحه شوید

از حالت تمام صفحه خارج شوید

عبور از لفظ رشته

ارسال یک رشته به عنوان اولین آرگومان به setTimeout به جای یک تابع می تواند منجر به مشکلات بالقوه شود و به طور کلی توصیه نمی شود.

مشکلاتی مشابه استفاده از eval() دارد.

در اینجا نمونه ای از پاس دادن لفظ رشته به آن آورده شده است setTimeout:

// Don’t do this
setTimeout(“console.log(‘Hello World!’);”, 500);

وارد حالت تمام صفحه شوید

از حالت تمام صفحه خارج شوید

در این مورد، رشته “console.log('Hello World!');” هنگامی که زمان منقضی می شود به عنوان کد در زمینه جهانی ارزیابی می شود.

با این حال، استفاده از یک رشته به این روش می‌تواند مشکلاتی ایجاد کند، زیرا ارزیابی در زمینه متفاوتی انجام می‌شود و نمادها یا متغیرهای محلی ممکن است در دسترس نباشند.

برای جلوگیری از این مشکلات، توصیه می شود یک تابع را به عنوان اولین آرگومان به آن ارسال کنید setTimeout در عوض این تضمین می کند که کد در زمینه صحیح اجرا شده و به نمادهای محلی دسترسی دارد.

در اینجا یک رویکرد جایگزین با استفاده از یک تابع به عنوان پاسخ تماس وجود دارد:

// Do this instead
setTimeout(() => {
console.log(‘Hello World!’)
}, 500)

وارد حالت تمام صفحه شوید

از حالت تمام صفحه خارج شوید

در این مثال، یک تابع فلش به عنوان پاسخ تماس استفاده می شود. تابع arrow روشی مختصر و ایمن برای اجرای کد پس از تاخیر مشخص شده ارائه می دهد.

از مشکلات مربوط به ارسال لفظ رشته به setTimeout جلوگیری می کند و تضمین می کند که کد در محدوده صحیح اجرا شده است.

با ارسال یک تابع به جای یک رشته، می توانید کنترل بهتری بر زمینه اجرا داشته باشید و از مشکلات احتمالی دسترسی به متغیرها یا نمادهای محلی جلوگیری کنید.

حداکثر مقدار تاخیر

حداکثر مقدار تاخیر قابل تنظیم در جاوا اسکریپت setTimeout تابع متد به پیاده سازی جاوا اسکریپت و محیطی که در آن اجرا می شود بستگی دارد.

در اکثر مرورگرهای مدرن و محیط های جاوا اسکریپت، حداکثر مقدار تاخیر تقریباً است 2^31 – 1 میلی ثانیه، که تقریباً *24.85 * روز اگر بخواهید مقدار تاخیری را بیشتر از این حداکثر تنظیم کنید، به طور خودکار به حداکثر مقدار مجاز بسته می شود.

بنابراین، اگر نیاز دارید کاری را برنامه ریزی کنید که بیش از این حداکثر تاخیر باشد، ممکن است لازم باشد رویکردهای جایگزین را در نظر بگیرید یا از ترکیبی از چندین مورد استفاده کنید. setTimeout تماس می گیرد.

شایان ذکر است که مقادیر تاخیر بسیار طولانی باید با احتیاط استفاده شوند، زیرا ممکن است برای بسیاری از سناریوهای دنیای واقعی قابل اعتماد یا عملی نباشند. اگر به زمان‌بندی دقیق یا تاخیرهای طولانی‌تری نیاز دارید، ممکن است بخواهید تکنیک‌ها یا API‌های دیگری را که به‌طور خاص برای چنین اهدافی طراحی شده‌اند، بررسی کنید.

در اینجا چند رویکرد جایگزین برای زمان‌بندی وظایفی که از حداکثر مقدار تاخیر فراتر می‌روند، آورده شده است:

از ترکیب چندگانه استفاده کنید setTimeout تماس می گیرد. این می تواند برای تقسیم یک کار طولانی به تکه های کوچکتر که می توانند به صورت جداگانه برنامه ریزی شوند استفاده شود.

از یک رشته یا فرآیند پس زمینه استفاده کنید. این می تواند برای اجرای وظایفی استفاده شود که نیازی به تعامل با موضوع اصلی یا رابط کاربری ندارند.

استفاده از a شخص ثالث کتابخانه یا API. تعدادی کتابخانه و API در دسترس هستند که از زمان‌بندی وظایف با تاخیر بیشتر پشتیبانی می‌کنند.

بهترین رویکرد برای زمان‌بندی کاری که از حداکثر مقدار تاخیر فراتر می‌رود، به نیازهای خاص آن کار بستگی دارد.

این این مشکل

هنگام استفاده setTimeout با یک روش، ممکن است با a مواجه شوید این مشکل کلمه کلیدی، جایی که مقدار این در داخل روش با انتظار شما متفاوت است.

این موضوع به دلیل راه پیش می آید setTimeout آثار و زمینه اجرای جداگانه ای که استفاده می کند.

به طور پیش فرض، زمانی که یک متد با استفاده از فراخوانی می شود setTimeout، این مقدار درون متد روی پنجره (یا سراسری) تنظیم شده است. شی به جای شی مورد نظر شما

این رفتار می تواند منجر به نتایج غیرمنتظره شود، همانطور که در مثال زیر نشان داده شده است:

const myArray = [‘zero’, ‘one’, ‘two’] myArray.myMethod = function (sProperty) {
console.log(arguments.length > 0 ? this[sProperty] : this)
}

myArray.myMethod() // prints “zero,one,two” (the whole array)
myArray.myMethod(1) // prints “one”

وارد حالت تمام صفحه شوید

از حالت تمام صفحه خارج شوید

در مثال بالا، وقتی myMethod به طور مستقیم فراخوانی می شود myArray، این مقدار به درستی تنظیم شده است myArray.

با این حال، هنگام استفاده setTimeout با myArray.myMethod، این مقدار به طور پیش فرض برای شی پنجره است.

برای غلبه بر این مشکل، چند راه حل وجود دارد که می توانید از آنها استفاده کنید:

یک رویکرد رایج استفاده از تابع wrapper است که به صراحت مقدار مورد نظر را تنظیم می کند:

setTimeout(function () {
myArray.myMethod()
}, 1000) // prints “zero,one,two” after 1 seconds

setTimeout(function () {
myArray.myMethod(‘1’)
}, 2500) // prints “one” after 2.5 seconds

وارد حالت تمام صفحه شوید

از حالت تمام صفحه خارج شوید

عملکرد پیکان به عنوان تابع wrapper:

توابع پیکان خود این مقدار را متصل نمی کنند و در عوض آن را از محدوده اطراف به ارث می برند.

این رفتار می تواند برای حفظ مقدار مورد انتظار در داخل تابع برگشت به تماس اعمال شود.

در اینجا مثالی از استفاده از یک تابع پیکان به عنوان یک تماس با setTimeout آورده شده است:

const myArray = [‘zero’, ‘one’, ‘two’]

setTimeout(() => {
myArray.myMethod()
}, 1000) // prints “zero,one,two” after 1 seconds

setTimeout(() => {
myArray.myMethod(‘1’)
}, 2500) // prints “one” after 2.5 seconds

وارد حالت تمام صفحه شوید

از حالت تمام صفحه خارج شوید

در این حالت، تابع فلش این اتصال مختص به خود را ندارد و در عوض از این مقدار از محدوده اطراف استفاده می کند که مقدار مورد انتظار است. myArray.

استفاده از یک تابع پیکان به عنوان یک پاسخ تماس می تواند راه حل مختصر و مناسبی برای این مشکل در هنگام کار با آن ارائه دهد setTimeout و روش ها

توجه به این نکته مهم است که عملکردهای پیکان در مقایسه با توابع معمولی تفاوت هایی در رفتار دارند، بنابراین ضروری است که مفاهیم آنها را در نظر بگیرید و مناسب ترین راه حل را بر اساس مورد استفاده خاص خود انتخاب کنید.

setTimeout(() => {
myArray.myMethod()
}, 1000) // prints “zero,one,two” after 1 seconds

setTimeout(() => {
myArray.myMethod(‘1’)
}, 2500) // prints “one” after 2.5 seconds

وارد حالت تمام صفحه شوید

از حالت تمام صفحه خارج شوید

Use bind: یکی دیگر از گزینه ها استفاده از bind() متد برای اتصال این مقدار مورد نظر به متد:

const myArray = [‘zero’, ‘one’, ‘two’] const myBoundMethod = function (sProperty) {
console.log(arguments.length > 0 ? this[sProperty] : this)
}.bind(myArray)

myBoundMethod() // prints “zero,one,two” because ‘this’ is bound to myArray in the function
myBoundMethod(1) // prints “one”

setTimeout(myBoundMethod, 1000) // still prints “zero,one,two” after 1 second due to the binding
setTimeout(myBoundMethod, 1500, ‘1’) // prints “one” after 1.5 seconds

وارد حالت تمام صفحه شوید

از حالت تمام صفحه خارج شوید

با استفاده از bind()، یک تابع جدید ایجاد می کنید که به طور دائم به این مقدار مشخص شده محدود می شود، و اطمینان حاصل می کنید که هنگام ارسال به setTimeout یا فراخوانی در جای دیگر ثابت می ماند.

این راه حل ها به حل این مشکل در هنگام استفاده کمک می کنند setTimeout با روش هایی که به شما امکان می دهد زمینه مورد نظر را حفظ کنید و از رفتار غیر منتظره اجتناب کنید.

مهلت زمانی تو در تو

تایم اوت های تودرتو به موقعیتی اشاره دارد که در آن a setTimeout تابع در تابع فراخوانی دیگری فراخوانی می شود setTimeout.

این رویکرد می تواند برای ایجاد توالی از رویدادهای زمان بندی شده یا ایجاد تاخیر بین اقدامات متوالی استفاده شود.

در اینجا یک مثال برای نشان دادن زمان های تو در تو وجود دارد:

setTimeout(function () {
console.log(‘First timeout executed.’)
setTimeout(function () {
console.log(‘Second timeout executed.’)
setTimeout(function () {
console.log(‘Third timeout executed.’)
}, 2000)
},1000)
}, 500)

وارد حالت تمام صفحه شوید

از حالت تمام صفحه خارج شوید

در این مثال، سه تابع setTimeout داریم که درون یکدیگر قرار گرفته اند. هر setTimeout عملکرد و تاخیر تماس خاص خود را دارد.

اولین setTimeout بعد از 500 میلی ثانیه اجرا می شود، دومی بعد از 1000 میلی ثانیه (1 ثانیه) از زمان اول اجرا می شود، و سومی بعد از 2000 میلی ثانیه (2 ثانیه) از زمان اوت دوم اجرا می شود.

هنگامی که این کد را اجرا می کنید، خروجی زیر را خواهد داشت:

First timeout executed.
Second timeout executed.
Third timeout executed.

وارد حالت تمام صفحه شوید

از حالت تمام صفحه خارج شوید

با تودرتو کردن زمان‌های زمانی، می‌توانید دنباله‌ای از اقدامات را ایجاد کنید که در بازه‌های زمانی مختلف رخ می‌دهند. این می تواند برای سناریوهایی مفید باشد که در آن شما نیاز به سازماندهی مجموعه ای از رویدادها یا ایجاد تاخیر بین عملیات خاص دارید.

با این حال، مهم است که به پیچیدگی بالقوه‌ای که می‌تواند از وقفه‌های زمانی عمیق تودرتو ناشی شود، توجه داشته باشید. با افزایش تعداد زمان های تودرتو، خواندن و نگهداری کد دشوارتر می شود.

در چنین مواردی، رویکردهای جایگزین مانند استفاده از همگام سازی/انتظار یا کتابخانه ها / چارچوب ها که عملیات ناهمزمان را مدیریت می کند ممکن است مناسب تر باشد.

به یاد داشته باشید که از تایم اوت های تودرتو استفاده کنید عاقلانه و بسته به پیچیدگی و الزامات کد خود گزینه های دیگری را در نظر بگیرید.

نتیجه گیری

این setTimeout تابع یک ابزار اساسی در جاوا اسکریپت است که توسعه دهندگان را قادر می سازد تا تجربیات پویا و تعاملی را در وب ایجاد کنند.

با تسلط بر setTimeout، توانایی کنترل زمان بندی، زمان بندی وظایف و ساخت برنامه های پیچیده را به دست می آورید. با دیدگاه‌ها و مثال‌هایی که در این وبلاگ به اشتراک گذاشته شده است، اکنون برای استفاده مؤثر از setTimeout و باز کردن پتانسیل کامل قابلیت‌های تایمر جاوا اسکریپت مجهز شده‌اید.

اکنون ابزار قدرتمندی برای انجام وظایف مربوط به زمان بندی، مدیریت تاخیرها و ایجاد برنامه های کاربردی وب تعاملی و پویاتر در اختیار دارید.

به یاد داشته باشید که setTimeout را تمرین و آزمایش کنید تا درک خود را عمیق تر کنید و پتانسیل کامل آن را باز کنید. با این دانش، شما به خوبی مجهز هستید تا از قدرت setTimeout استفاده کنید و عملکرد برنامه های جاوا اسکریپت خود را افزایش دهید.

کد نویسی مبارک 🙂

منبع

مقدمه

جاوا اسکریپت یک زبان برنامه نویسی قدرتمند است که به توسعه دهندگان اجازه می دهد تا برنامه های وب پویا و تعاملی ایجاد کنند. یکی از ویژگی های مهم جاوا اسکریپت تابع متد Javascript setTimeout است که انتظار جاوا اسکریپت را فعال می کند.

درک نحوه استفاده موثر setTimeout برای کنترل زمان و جریان برنامه های جاوا اسکریپت شما بسیار مهم است. در این راهنمای جامع، عمیقاً به دنیای جاوا اسکریپت خواهیم پرداخت setTimeout روش و کارکردهای مختلف آن را بررسی کنید.

چه مبتدی یا یک توسعه دهنده با تجربه باشید، این مقاله تمام دانشی را که برای استفاده از پتانسیل کامل نیاز دارید در اختیار شما قرار می دهد. setTimeout در پروژه های جاوا اسکریپت شما

بنابراین، برای تسلط بر هنر زمان‌بندی در جاوا اسکریپت آماده شوید و امکانات جدیدی را برای ایجاد برنامه‌های کاربردی وب پاسخگو و کارآمد باز کنید.

بیایید به دنیای کاوش کنیم setTimeout و تمام اسرار آن را کشف کنید!

پیش نیازها

قبل از کاوش در دنیای setTimeout، داشتن درک اولیه از جاوا اسکریپت و مفاهیم اساسی آن مفید است. آشنایی با متغیرها، توابع و جریان اصلی کنترل (مانند دستورات if و حلقه ها) درک مفاهیم مورد بحث در این مقاله را آسان تر می کند.

اگر به تازگی با جاوا اسکریپت آشنا شده اید یا به یک تجدید کننده نیاز دارید، منابع آنلاین متعددی برای یادگیری اصول اولیه وجود دارد. وب‌سایت‌هایی مانند MDN Web Docs، W3Schools و freeCodeCamp آموزش‌ها و راهنماهای جامعی را ارائه می‌دهند که می‌تواند به شما در شروع سفر جاوا اسکریپت کمک کند.

علاوه بر این، من دو کتاب زیر را برای مبتدیان در جاوا اسکریپت به شدت توصیه می کنم:

برنامه نویسی Head First JavaScript: راهنمای مناسب برای مغز

جاوا اسکریپت: راهنمای قطعی: بر پرکاربردترین زبان برنامه نویسی جهان مسلط شوید

(و بله من آنها را رایگان ارائه می کنم)

با غواصی در این منابع، پایه محکمی در برنامه نویسی جاوا اسکریپت به دست خواهید آورد و شما را به دانش لازم برای کشف پیچیدگی های setTimeout و باز کردن امکانات جدید در پروژه های توسعه وب خود مجهز می کند.

بنابراین، قبل از اینکه به پیچیدگی های آن بپردازیم setTimeout، مطمئن شوید که یک پایه محکم در برنامه نویسی جاوا اسکریپت دارید.

وقتی آماده شدید، بیایید قدرت آن را بررسی کنیم setTimeout و امکانات جدید را در پروژه های توسعه وب خود باز کنید.

هدف از setTimeout

برای شروع، بیایید هدف را درک کنیم setTimeout اول

setTimeout معمولاً در سناریوهایی استفاده می‌شود که می‌خواهید تاخیرها، برنامه‌ریزی رویدادها یا انجام وظایف را در بازه‌های زمانی مشخص انجام دهید.

کمی گیج کننده درست است؟

بیایید با یک مثال این را بفهمیم:

توجه: لطفاً فعلاً در مورد نحو آن فکر نکنید. بعداً در مورد Syntex بحث خواهیم کرد.

فرض کنید می خواهید یک تابع را اعلام کنید اما به جای فراخوانی فوری آن، می خواهید آن را پس از مدت زمان مشخصی فراخوانی کنید.

اینجاست که setTimeout وارد تصویر می شود این قابلیت را برای به تاخیر انداختن اجرای یک تابع فراهم می کند.

به کد زیر دقت کنید:

function greetUser() {  
 console.log('Hello, user!') 
}  
setTimeout(greetUser, 1000)
وارد حالت تمام صفحه شوید

از حالت تمام صفحه خارج شوید

در این مثال تابعی به نام داریم greetUser که به سادگی یک پیام تبریک را به کنسول ثبت می کند. می خواهیم اجرای این تابع را 1 ثانیه به تاخیر بیندازیم.

برای رسیدن به این هدف، از setTimeout عملکرد و عبور از greetUser تابع به عنوان آرگومان اول و 1000 به عنوان آرگومان دوم.

و بس!

هنگامی که این کد را اجرا می کنید، جاوا اسکریپت 1 ثانیه منتظر می ماند و سپس پیام تبریک “Hello, user!” به کنسول

نحو و پارامترهای ** setTimeout**

برای استفاده موثر setTimeout، درک نحو و پارامترهای آن مهم است.

نحو اساسی از setTimeout به شرح زیر است:

setTimeout(function, delay, param1, param2, ...);
وارد حالت تمام صفحه شوید

از حالت تمام صفحه خارج شوید

بیایید اجزای مختلف را تجزیه کنیم:

اولین پارامتر تابع یا قطعه کدی است که می خواهید پس از تاخیر مشخص شده اجرا کنید. این می تواند یک تابع با نام یا یک تابع ناشناس باشد.

تاخیر پارامتر دوم نشان دهنده فاصله زمانی بر حسب میلی ثانیه قبل از شروع اجرای کد است. مدت زمان تأخیر را قبل از فراخوانی تابع مشخص شده تعیین می کند.

پارامترهای اضافی مانند param1، param2 و غیره اختیاری هستند. می توانید از آنها برای ارسال آرگومان ها به تابع مشخص شده در پارامتر اول استفاده کنید.

اینها setTimeout پارامترها به شما این امکان را می دهند که رفتار تابع را هنگام اجرا سفارشی کنید.

این setTimeout() **یک **timeoutID را برمی گرداند که یک عدد صحیح مثبت است که تایمر ایجاد شده در نتیجه فراخوانی متد را شناسایی می کند. این شناسه زمان پایان می توان از آن برای لغو مهلت با ارسال آن به clearTimeout() روشی که در مقاله ای دیگر به آن خواهیم پرداخت.

توجه: اگر نحو را گیج کننده می بینید، نگران نباشید!

در بخش‌های آینده این وبلاگ، نمونه‌های مختلف و موارد استفاده برای هر پارامتر را با جزئیات بررسی خواهیم کرد. من به شما اطمینان می دهم که با خواندن مقاله کامل، درک واضحی از نحوه استفاده به دست خواهید آورد setTimeout به طور موثر

بنابراین، صبور باشید و به خواندن ادامه دهید تا پتانسیل کامل این عملکرد قدرتمند جاوا اسکریپت را باز کنید.

تجزیه کد setTimeout

من می دانم که شما قبلاً متوجه شده اید که چه اتفاقی برای کدی که قبلاً استفاده می کردیم، افتاده است. اما برای تقویت درک خود، بیایید کد را با هم بشکنیم:

function greetUser() {
  console.log('Hello, user!')
}

setTimeout(greetUser, 1000)
وارد حالت تمام صفحه شوید

از حالت تمام صفحه خارج شوید

در این قطعه کد:

  1. ما یک تابع به نام تعریف می کنیم greetUser با استفاده از کلمه کلیدی تابع این تابع وظیفه چاپ پیام تبریک به کنسول را بر عهده دارد.

  2. ما استفاده می کنیم setTimeout تابع زمانبندی اجرای greetUser عملکرد پس از یک تاخیر مشخص تاخیر روی 1000 میلی ثانیه تنظیم شده است که معادل 1 ثانیه است.

  3. اولین استدلال به تصویب رسید setTimeout مرجع تابع است greetUser. این می گوید setTimeout کدام تابع را پس از تأخیر مشخص شده اجرا کنید.

  4. آرگومان دوم 1000 نشان دهنده تاخیر در میلی ثانیه است. دوره زمانی قبل از شروع اجرای کد را تعیین می کند.

با استفاده از setTimeout، به جاوا اسکریپت دستور می دهیم 1 ثانیه صبر کنید و سپس آن را فراخوانی می کنیم greetUser تابع در نتیجه پیام تبریک “سلام کاربر!” روی کنسول چاپ خواهد شد.

استفاده از تابع ناشناس به عنوان پاسخ تماس

در مثال کد قبلی، از یک تابع با نام به عنوان تابع callback در کد استفاده کردیم setTimeout تابع

با این حال، setTimeout همچنین به شما این امکان را می دهد که یک تابع ناشناس را به عنوان یک فراخوان ارائه کنید که پس از تاخیر مشخص شده اجرا می شود.

توابع ناشناس معمولاً زمانی استفاده می شوند که کدی که باید اجرا شود ساده است و نیازی به یک تابع نام جداگانه ندارد.

در اینجا یک مثال است:

setTimeout(function () {  
 console.log('This code executes after the delay') 
}, 1000)

وارد حالت تمام صفحه شوید

از حالت تمام صفحه خارج شوید

در این مورد، تابع ناشناس به عنوان پاسخ به تماس عمل می کند. پس از 1000 میلی ثانیه (یا 1 ثانیه) یک پیام را به کنسول ثبت می کند.

می توانید جایگزین کنید console.log عبارت با هر کدی که می خواهید بعد از تاخیر اجرا کنید. استفاده از توابع ناشناس به عنوان تماس در setTimeout انعطاف پذیری را فراهم می کند و به شما امکان می دهد بدون نیاز به اعلان عملکرد جداگانه، کد را به صورت درون خطی تعریف و اجرا کنید.

ارسال آرگومان ها به تابع callback

در setTimeout تابع callback، شما به راحتی می توانید پارامترها یا آرگومان ها را ارسال کنید.

فرض کنید تابعی دارید که پارامترها را می‌پذیرد و می‌خواهید زمانی که تابع پس از تأخیر اجرا می‌شود، مقادیر خاصی برای آن پارامترها ارائه دهید:

function greet(name) {   
  console.log('Hello, ' + name + '!') 
}  

setTimeout(greet, 5000, 'John')

وارد حالت تمام صفحه شوید

از حالت تمام صفحه خارج شوید

در این مثال، تابع greet برنامه ریزی شده است که 5 ثانیه (5000 میلی ثانیه) صبر کند و آرگومان جان به عنوان پارامتر نام ارسال می شود.

شما می توانید تاخیر و مقادیر آرگومان را با توجه به مورد خاص خود تنظیم کنید.

با استفاده از این رویکرد، می‌توانید رفتار تابع callback را با ارسال مقادیر مختلف به عنوان آرگومان سفارشی کنید و امکان اجرای کد پویا و انعطاف‌پذیرتر را فراهم کنید.

در اینجا چند نکته اضافی برای ارسال آرگومان ها به تابع callback آورده شده است:

  • شما می توانید هر تعداد آرگومان را به تابع callback ارسال کنید.
  • آرگومان ها به همان ترتیبی که به آن ارسال شدند به تابع callback ارسال می شوند setTimeout.
  • اگر تعداد متغیری از آرگومان ها را به تابع callback ارسال کنید، می توانید از شی آرگومان ها برای دسترسی به آنها استفاده کنید.

در زیر مثالی آورده شده است:

function processArgs() {
  for (let i = 0; i < arguments.length; i++) {
    console.log("Argument " + (i + 1) + ": " + arguments[i]);
  }
}

setTimeout(processArgs, 1000, "apple", "banana", "cherry");

وارد حالت تمام صفحه شوید

از حالت تمام صفحه خارج شوید

در این مثال، processArgs تابع هر آرگومان را به همراه شاخص مربوط به آن در کنسول چاپ می کند. خروجی خواهد بود:

Argument 1: apple
Argument 2: banana
Argument 3: cherry

وارد حالت تمام صفحه شوید

از حالت تمام صفحه خارج شوید

عبور از لفظ رشته

ارسال یک رشته به عنوان اولین آرگومان به setTimeout به جای یک تابع می تواند منجر به مشکلات بالقوه شود و به طور کلی توصیه نمی شود.

مشکلاتی مشابه استفاده از eval() دارد.

در اینجا نمونه ای از پاس دادن لفظ رشته به آن آورده شده است setTimeout:

// Don't do this 
setTimeout("console.log('Hello World!');", 500);
وارد حالت تمام صفحه شوید

از حالت تمام صفحه خارج شوید

در این مورد، رشته “console.log('Hello World!');” هنگامی که زمان منقضی می شود به عنوان کد در زمینه جهانی ارزیابی می شود.

با این حال، استفاده از یک رشته به این روش می‌تواند مشکلاتی ایجاد کند، زیرا ارزیابی در زمینه متفاوتی انجام می‌شود و نمادها یا متغیرهای محلی ممکن است در دسترس نباشند.

برای جلوگیری از این مشکلات، توصیه می شود یک تابع را به عنوان اولین آرگومان به آن ارسال کنید setTimeout در عوض این تضمین می کند که کد در زمینه صحیح اجرا شده و به نمادهای محلی دسترسی دارد.

در اینجا یک رویکرد جایگزین با استفاده از یک تابع به عنوان پاسخ تماس وجود دارد:

// Do this instead 
setTimeout(() => {
   console.log('Hello World!') 
}, 500)

وارد حالت تمام صفحه شوید

از حالت تمام صفحه خارج شوید

در این مثال، یک تابع فلش به عنوان پاسخ تماس استفاده می شود. تابع arrow روشی مختصر و ایمن برای اجرای کد پس از تاخیر مشخص شده ارائه می دهد.

از مشکلات مربوط به ارسال لفظ رشته به setTimeout جلوگیری می کند و تضمین می کند که کد در محدوده صحیح اجرا شده است.

با ارسال یک تابع به جای یک رشته، می توانید کنترل بهتری بر زمینه اجرا داشته باشید و از مشکلات احتمالی دسترسی به متغیرها یا نمادهای محلی جلوگیری کنید.

حداکثر مقدار تاخیر

حداکثر مقدار تاخیر قابل تنظیم در جاوا اسکریپت setTimeout تابع متد به پیاده سازی جاوا اسکریپت و محیطی که در آن اجرا می شود بستگی دارد.

در اکثر مرورگرهای مدرن و محیط های جاوا اسکریپت، حداکثر مقدار تاخیر تقریباً است 2^31 – 1 میلی ثانیه، که تقریباً *24.85 * روز اگر بخواهید مقدار تاخیری را بیشتر از این حداکثر تنظیم کنید، به طور خودکار به حداکثر مقدار مجاز بسته می شود.

بنابراین، اگر نیاز دارید کاری را برنامه ریزی کنید که بیش از این حداکثر تاخیر باشد، ممکن است لازم باشد رویکردهای جایگزین را در نظر بگیرید یا از ترکیبی از چندین مورد استفاده کنید. setTimeout تماس می گیرد.

شایان ذکر است که مقادیر تاخیر بسیار طولانی باید با احتیاط استفاده شوند، زیرا ممکن است برای بسیاری از سناریوهای دنیای واقعی قابل اعتماد یا عملی نباشند. اگر به زمان‌بندی دقیق یا تاخیرهای طولانی‌تری نیاز دارید، ممکن است بخواهید تکنیک‌ها یا API‌های دیگری را که به‌طور خاص برای چنین اهدافی طراحی شده‌اند، بررسی کنید.

در اینجا چند رویکرد جایگزین برای زمان‌بندی وظایفی که از حداکثر مقدار تاخیر فراتر می‌روند، آورده شده است:

از ترکیب چندگانه استفاده کنید setTimeout تماس می گیرد. این می تواند برای تقسیم یک کار طولانی به تکه های کوچکتر که می توانند به صورت جداگانه برنامه ریزی شوند استفاده شود.

از یک رشته یا فرآیند پس زمینه استفاده کنید. این می تواند برای اجرای وظایفی استفاده شود که نیازی به تعامل با موضوع اصلی یا رابط کاربری ندارند.

استفاده از a شخص ثالث کتابخانه یا API. تعدادی کتابخانه و API در دسترس هستند که از زمان‌بندی وظایف با تاخیر بیشتر پشتیبانی می‌کنند.

بهترین رویکرد برای زمان‌بندی کاری که از حداکثر مقدار تاخیر فراتر می‌رود، به نیازهای خاص آن کار بستگی دارد.

این این مشکل

هنگام استفاده setTimeout با یک روش، ممکن است با a مواجه شوید این مشکل کلمه کلیدی، جایی که مقدار این در داخل روش با انتظار شما متفاوت است.

این موضوع به دلیل راه پیش می آید setTimeout آثار و زمینه اجرای جداگانه ای که استفاده می کند.

به طور پیش فرض، زمانی که یک متد با استفاده از فراخوانی می شود setTimeout، این مقدار درون متد روی پنجره (یا سراسری) تنظیم شده است. شی به جای شی مورد نظر شما

این رفتار می تواند منجر به نتایج غیرمنتظره شود، همانطور که در مثال زیر نشان داده شده است:

const myArray = ['zero', 'one', 'two']
myArray.myMethod = function (sProperty) {
  console.log(arguments.length > 0 ? this[sProperty] : this)
}

myArray.myMethod() // prints "zero,one,two" (the whole array)
myArray.myMethod(1) // prints "one"

وارد حالت تمام صفحه شوید

از حالت تمام صفحه خارج شوید

در مثال بالا، وقتی myMethod به طور مستقیم فراخوانی می شود myArray، این مقدار به درستی تنظیم شده است myArray.

با این حال، هنگام استفاده setTimeout با myArray.myMethod، این مقدار به طور پیش فرض برای شی پنجره است.

برای غلبه بر این مشکل، چند راه حل وجود دارد که می توانید از آنها استفاده کنید:

یک رویکرد رایج استفاده از تابع wrapper است که به صراحت مقدار مورد نظر را تنظیم می کند:

setTimeout(function () { 
    myArray.myMethod() 
}, 1000) // prints "zero,one,two" after 1 seconds

setTimeout(function () { 
   myArray.myMethod('1') 
}, 2500) // prints "one" after 2.5 seconds

وارد حالت تمام صفحه شوید

از حالت تمام صفحه خارج شوید

  • عملکرد پیکان به عنوان تابع wrapper:

توابع پیکان خود این مقدار را متصل نمی کنند و در عوض آن را از محدوده اطراف به ارث می برند.

این رفتار می تواند برای حفظ مقدار مورد انتظار در داخل تابع برگشت به تماس اعمال شود.

در اینجا مثالی از استفاده از یک تابع پیکان به عنوان یک تماس با setTimeout آورده شده است:

  const myArray = ['zero', 'one', 'two'] 

  setTimeout(() => {
   myArray.myMethod() 
  }, 1000) // prints "zero,one,two" after 1 seconds 

  setTimeout(() => {
   myArray.myMethod('1') 
  }, 2500) // prints "one" after 2.5 seconds

وارد حالت تمام صفحه شوید

از حالت تمام صفحه خارج شوید

در این حالت، تابع فلش این اتصال مختص به خود را ندارد و در عوض از این مقدار از محدوده اطراف استفاده می کند که مقدار مورد انتظار است. myArray.

استفاده از یک تابع پیکان به عنوان یک پاسخ تماس می تواند راه حل مختصر و مناسبی برای این مشکل در هنگام کار با آن ارائه دهد setTimeout و روش ها

توجه به این نکته مهم است که عملکردهای پیکان در مقایسه با توابع معمولی تفاوت هایی در رفتار دارند، بنابراین ضروری است که مفاهیم آنها را در نظر بگیرید و مناسب ترین راه حل را بر اساس مورد استفاده خاص خود انتخاب کنید.

  setTimeout(() => {
    myArray.myMethod()
  }, 1000) // prints "zero,one,two" after 1 seconds

  setTimeout(() => {
    myArray.myMethod('1')
  }, 2500) // prints "one" after 2.5 seconds

وارد حالت تمام صفحه شوید

از حالت تمام صفحه خارج شوید

  • Use bind: یکی دیگر از گزینه ها استفاده از bind() متد برای اتصال این مقدار مورد نظر به متد:
  const myArray = ['zero', 'one', 'two']
  const myBoundMethod = function (sProperty) {
    console.log(arguments.length > 0 ? this[sProperty] : this)
  }.bind(myArray)

  myBoundMethod() // prints "zero,one,two" because 'this' is bound to myArray in the function
  myBoundMethod(1) // prints "one"

  setTimeout(myBoundMethod, 1000) // still prints "zero,one,two" after 1 second due to the binding
  setTimeout(myBoundMethod, 1500, '1') // prints "one" after 1.5 seconds

وارد حالت تمام صفحه شوید

از حالت تمام صفحه خارج شوید

با استفاده از bind()، یک تابع جدید ایجاد می کنید که به طور دائم به این مقدار مشخص شده محدود می شود، و اطمینان حاصل می کنید که هنگام ارسال به setTimeout یا فراخوانی در جای دیگر ثابت می ماند.

این راه حل ها به حل این مشکل در هنگام استفاده کمک می کنند setTimeout با روش هایی که به شما امکان می دهد زمینه مورد نظر را حفظ کنید و از رفتار غیر منتظره اجتناب کنید.

مهلت زمانی تو در تو

تایم اوت های تودرتو به موقعیتی اشاره دارد که در آن a setTimeout تابع در تابع فراخوانی دیگری فراخوانی می شود setTimeout.

این رویکرد می تواند برای ایجاد توالی از رویدادهای زمان بندی شده یا ایجاد تاخیر بین اقدامات متوالی استفاده شود.

در اینجا یک مثال برای نشان دادن زمان های تو در تو وجود دارد:

setTimeout(function () { 
  console.log('First timeout executed.') 
   setTimeout(function () {
     console.log('Second timeout executed.')
      setTimeout(function () {
       console.log('Third timeout executed.')
     }, 2000)
   },1000)
 }, 500)

وارد حالت تمام صفحه شوید

از حالت تمام صفحه خارج شوید

در این مثال، سه تابع setTimeout داریم که درون یکدیگر قرار گرفته اند. هر setTimeout عملکرد و تاخیر تماس خاص خود را دارد.

اولین setTimeout بعد از 500 میلی ثانیه اجرا می شود، دومی بعد از 1000 میلی ثانیه (1 ثانیه) از زمان اول اجرا می شود، و سومی بعد از 2000 میلی ثانیه (2 ثانیه) از زمان اوت دوم اجرا می شود.

هنگامی که این کد را اجرا می کنید، خروجی زیر را خواهد داشت:

First timeout executed. 
Second timeout executed. 
Third timeout executed.

وارد حالت تمام صفحه شوید

از حالت تمام صفحه خارج شوید

با تودرتو کردن زمان‌های زمانی، می‌توانید دنباله‌ای از اقدامات را ایجاد کنید که در بازه‌های زمانی مختلف رخ می‌دهند. این می تواند برای سناریوهایی مفید باشد که در آن شما نیاز به سازماندهی مجموعه ای از رویدادها یا ایجاد تاخیر بین عملیات خاص دارید.

با این حال، مهم است که به پیچیدگی بالقوه‌ای که می‌تواند از وقفه‌های زمانی عمیق تودرتو ناشی شود، توجه داشته باشید. با افزایش تعداد زمان های تودرتو، خواندن و نگهداری کد دشوارتر می شود.

در چنین مواردی، رویکردهای جایگزین مانند استفاده از همگام سازی/انتظار یا کتابخانه ها / چارچوب ها که عملیات ناهمزمان را مدیریت می کند ممکن است مناسب تر باشد.

به یاد داشته باشید که از تایم اوت های تودرتو استفاده کنید عاقلانه و بسته به پیچیدگی و الزامات کد خود گزینه های دیگری را در نظر بگیرید.

نتیجه گیری

این setTimeout تابع یک ابزار اساسی در جاوا اسکریپت است که توسعه دهندگان را قادر می سازد تا تجربیات پویا و تعاملی را در وب ایجاد کنند.

با تسلط بر setTimeout، توانایی کنترل زمان بندی، زمان بندی وظایف و ساخت برنامه های پیچیده را به دست می آورید. با دیدگاه‌ها و مثال‌هایی که در این وبلاگ به اشتراک گذاشته شده است، اکنون برای استفاده مؤثر از setTimeout و باز کردن پتانسیل کامل قابلیت‌های تایمر جاوا اسکریپت مجهز شده‌اید.

اکنون ابزار قدرتمندی برای انجام وظایف مربوط به زمان بندی، مدیریت تاخیرها و ایجاد برنامه های کاربردی وب تعاملی و پویاتر در اختیار دارید.

به یاد داشته باشید که setTimeout را تمرین و آزمایش کنید تا درک خود را عمیق تر کنید و پتانسیل کامل آن را باز کنید. با این دانش، شما به خوبی مجهز هستید تا از قدرت setTimeout استفاده کنید و عملکرد برنامه های جاوا اسکریپت خود را افزایش دهید.

کد نویسی مبارک 🙂

منبع

نوشته های مشابه

دیدگاهتان را بنویسید

نشانی ایمیل شما منتشر نخواهد شد. بخش‌های موردنیاز علامت‌گذاری شده‌اند *

دکمه بازگشت به بالا