با سلام و عرض احترام خدمت همراهان همیشگی روکسو، در این جلسه قصد داریم در رابطه با موضوعی بسیار مهم از دنیای توابع جاوا اسکریپتی با شما صحبت کنیم: پارامترها (یا آرگومان ها) و تاثیرشان در تغییر مقادیر اصلی و ارجاعات. ممکن است متوجه جمله ی من نشوید، مشکلی نیست! این مقاله را بخوانید تا با انواع پارامترهای جاوا اسکریپتی آشنا شوید.
اگر از دوره ی قبل به یاد داشته باشید، توابع جاوا اسکریپتی می توانستند مقادیری به نام پارامتر یا آرگومان بگیرند:
function functionName(parameter1, parameter2, parameter3) { // کد های مورد نظر ما برای اجرا شدن }
و در مورد تفاوت کلمات «پارامتر» و «آرگومان» توضیح دادیم که:
توابع جاوا اسکریپت هیچ تست و آزمایشی روی پارامترهای خود انجام نمی دهند بنابراین هیچ نوع داده ی مشخص شده ای وجود ندارد و شما می توانید هر مقداری را به توابع پاس دهید. با توجه به این مسئله اگر به توابع تعداد آرگومان هایی کافی داده نشود (به طور مثال یکی از آرگومان ها را به تابع ندهیم)، تابع به صورت خودکار به جای آن آرگومان ها مقدار undefined قرار می دهد.
برخی اوقات این مسئله مشکلی ایجاد نمی کند اما بهتر است برای جلوگیری از ایجاد خطا در برنامه هایتان همیشه از مقادیر پیش فرض استفاده کنید. به مثال زیر دقت کنید:
<!DOCTYPE html> <html> <body> <p>Setting a default value to a function parameter.</p> <p id="demo"></p> <script> function myFunction(x, y) { if (y === undefined) { y = 0; } return x * y; } document.getElementById("demo").innerHTML = myFunction(4); </script> </body> </html>
به همین شکل و با استفاده از یک شرط اضافی می توانیم از ایجاد مقادیر undefined جلوگیری کنیم. البته نکته ی جالب اینجاست که در ECMAScript 2015 می توان این کار را به شکل بسیار راحت تری انجام داد:
function (a=1, b=1) { // function code }
سوال: ECMAScript 2015 در چه مرورگرهایی پشتیبانی می شود؟
پاسخ: از نامش مشخص است! تمام مرورگر های امروزی از آن پشتیبانی می کنند و مشکلی در اجرای کدهایتان نخواهید داشت. Internet Explorer 9, Firefox 4 Chrome 5, Safari 5 و نسخه های بعدی شان تماما از آن پشتیبانی می کنند. می توانید به صفحه ی kangax.github.io مراجعه و به صورت مفصل و لیست شده انواع پشتیبانی های مرورگر های مختلف را مشاهده کنید. در یک کلام، با خیال راحت از آن استفاده کنید.
توابع جاوا اسکریپتی شیء ای از پیش ساخته شده دارند به نام arguments object که شامل آرایه ای از آرگومان هایی است که هنگام فراخوانی تابع استفاده شده اند. شما می توانید بر این اساس از تابعی استفاده کنید که بیشترین مقدار را بین مقادیر مختلف به شما می دهد:
<!DOCTYPE html> <html> <body> <p>Finding the largest number.</p> <p id="demo"></p> <script> function findMax() { var i; var max = -Infinity; for(i = 0; i < arguments.length; i++) { if (arguments[i] > max) { max = arguments[i]; } } return max; } document.getElementById("demo").innerHTML = findMax(4, 5, 6); </script> </body> </html>
در این تابع به کلمات arguments
و max
توجه داشته باشید، اینها از شیء آرگومان می آیند.
همچنین می توانید با همین روش مجموع مقادیر مختلف را به دست آورید:
<!DOCTYPE html> <html> <body> <p>Sum of all arguments:</p> <p id="demo"></p> <script> function sumAll() { var i; var sum = 0; for(i = 0; i < arguments.length; i++) { sum += arguments[i]; } return sum; } document.getElementById("demo").innerHTML = sumAll(1, 123, 500, 115, 44, 88); </script> </body> </html>
می بینید که به راحتی و با روشی شاید عجیب و غریب توانستیم مجموع مقادیر پارامترهایمان را به دست بیاوریم. باید به شما بگویم که راه های بسیار زیادی برای این کار وجود دارد و این روش، تنها روش موجود نیست. شما می توانید با ورود به صفحه ی JSBin (خروجی کد) و بازی کردن با کدها (مخصوصا شیء آرگومان، مانند arguments
) بر این بحث تسلط پیدا کنید.
آرگومان ها از نوع Passed by Value هستند: این مسئله بدین معنی است که تابع تنها مقادیر (value ها) را می شناسد، نه مکان آرگومان ها را. بنابراین اگر تابعی مقدار آرگومانی را تغییر دهد، مقدار اولیه ی آن پارامتر تغییری نمی کند. بگذارید ساده تر بگویم؛ pass by value به معنی پاس دادن خودِ مقدار است. بنابراین اگر متغیری به نام X را به عنوان آرگومان به تابعی دهیم:
<!DOCTYPE html> <html> <body> <p id="OriginalValueOfX"></p> <p id="NewValueOfX"></p> <script> var x = 10; function passByValue (ValueOfX) { ValueOfX++; document.getElementById("NewValueOfX").innerHTML = ValueOfX; } passByValue(x); document.getElementById("OriginalValueOfX").innerHTML = x; </script> </body> </html>
در مثال بالا ابتدا یک متغیر به نام x تعریف کردیم و به آن مقدار 10 را دادیم. سپس داخل تابعی به نام passByValue، مقدار x را عوض کرده و یک عدد به آن اضافه کردیم تا مساوی با 11 بشود اما اگر خروجی را ببینید متوجه می شوید که مقدار اصلی x دست نخورده است و هنوز همان 10 می باشد. چرا؟ به این دلیل که آرگومان ها در جاوا اسکریپت از نوع Pass by Value هستند؛ یعنی با متغیر X کاری ندارند بلکه مقدارِ x (یعنی عدد 10) را برمیدارند و عملیات را روی عدد 10 انجام می دهند. بدین صورت، خود متغیر x هیچ تغییری نمی کند.
اشیاء از نوع Passed by Reference هستند: برخلاف آرگومان ها اشیاء از جنس Passed by Reference هستند بنابراین اگر تابعی خصوصیت (property) یک تابع را تغییر دهد، مقدار اصلی خصوصیت نیز تغییر پیدا می کند. به مثال زیر دقت کنید:
<!DOCTYPE html> <html> <body> <p id="demo"></p> <script> var person = { firstname:"John", lastname:"Doe", age:50, eyecolor:"blue" }; function changeAge (){ person.age = 80; } changeAge(); document.getElementById("demo").innerHTML = person.firstname + " is " + person.age + " years old."; </script> </body> </html>
به خروجی کد بالا بروید و خط 19 کد (;()changeAge
) را حذف کنید. به خروجی نگاه و سپس دوباره این خط را اضافه کنید. میبینید با اجرای تابع، خصوصیت شیء کاملا عوض می شود. Pass by reference یعنی پاس دادنِ ارجاع؛ بنابراین به جای آنکه عدد 50 گرفته شود و به تابع داده شود، خودِ خصوصیت age، که به عدد 50 ارجاع می دهد، به تابع داده می شود.
امیدوارم از این قسمت لذت برده باشید. در قسمت بعد در رابطه با فراخوانی توابع و نکات پیرامون آن بحث خواهیم کرد.
در این قسمت، به پرسشهای تخصصی شما دربارهی محتوای مقاله پاسخ داده نمیشود. سوالات خود را اینجا بپرسید.
در این قسمت، به پرسشهای تخصصی شما دربارهی محتوای مقاله پاسخ داده نمیشود. سوالات خود را اینجا بپرسید.
در این قسمت، به پرسشهای تخصصی شما دربارهی محتوای مقاله پاسخ داده نمیشود. سوالات خود را اینجا بپرسید.