تعداد بازدید: 505

توابع در جاوا اسکریپت (قسمت سوم)

this یک شئ است از موجودیت تعریف شده در جریان برنامه . به طور مثال Person می تواند موجودیت تعریف شده برای هر فرد باشد و در آن برای ارجاع به شئ جاری در Action ها می توان از کلمه کلیدی this استفاده کرد. اگر قرار باشد به محاوره معنی this را بگوییم برابر myself است .

در زبان جاوا اسکریپت شما می توانید از کلمه کلیدی this در ناحیه عمومی یا همان global scope و همچنین در تمامی توابع (از جنس function , closure , methods …) استفاده کنید. البته تفاوت هایی در حالت های strict mode , none strict mode است.

Function Execution Context

مقاد یک تابع به صورت کلی شامل موارد زیر است :

  • Arguments : آرگومان های ورودی یک تابع
  • Variable Scope : متغیر هایی که در این ناحیه قابل دستیابی است .
  • this Object : متغیر this موجود در این تابع که خود در بردارنده متغیر هایی می تواند باشد.

function context model A Function Context (red) B Function Context (blue) C Function Context (green)

در مثال بالا ما به صورت کلی ساختار داخلی یا مفاد تابع C را در تصویر زمانی که در دو تابع دیگر قرار گرفته شده است را در سمت چپ تصویر نمایش داده ایم که شامل تمامی متغیر های scope بالا تر به علاوه آرگومان ها و this می باشد.

This Keyword

کلمه کلیدی this متعلق است به شئ جاری از Object Wrapper مورد نظر . پس برای این که بفهمیم tکلمه کلیدی this به چه نوع شئ اشاره دارد باید ابتدا بفهمیم که Object Wrapper این تابع چیست . در مثال زیر this برابر است با BOM چون این تابع در ناحیه عمومی تعریف شده است و در global scope کلمه کلیدی this برابر است با window .

function foo(){
  console.log(this)
}

foo() //Window https://gnutec.net/?p=2484&preview=true

در مثال زیر this برابر است با Object Wrapper تعیین شده در این بلوک کد که person نام دارد. چون در تابع whoAmI در Person Object Wrapper قرار دارد برای همین می توان گفت که this برابر با همین شئ است که از روی آن ساختیم.

var Person = {
    name: 'nobody',
    setName: function(name){
        this.name = name
    },
    whoAmI: function(){
        console.log(this)
    }
}
var ali = Object.create(Person)
ali.whoAmI() //Object {  }

در رابطه با کلاس هم به همین منوال است . متدی که در کلاس قرار گرفته است this در آن برابر است با شئ که از روی آن کلاس ساخته ایم .

class Car{
    run(){
        console.log('wooowww',this)
    }
}
var cadi = new Car
cadi.run() //'wooowww' Object {  }

پس این که این تابع در کدام Object Wrapper قرار گرفته است تعیین کننده این است که شئ this در این تابع یا متد از چه نوع است .

  • در Object Methods کلمه کلیدی this برابر همان object است.
  • در global scope کلمه کلیدی در Browser Environment برابر window است.
  • در توابعی که در global scope تعریف شده باشند this برابر window است. اگر حالت strict mode فعال باشد برابر undefined است.
  • در event ها this برابر همان Element Node که event روی آن trigger شده است.
  • با استفاده از Function Constructor Method های call,apply,bind ما می توانیم this در جریان تابع را تغییر بدهیم.

JavaScript Environment

محیط اجرای جاوا اسکریپت که در آن مفسر جاوا اسکریپت (Javascript Interpreter) تعبیه شده است محیط اجرای جاوا اسکریپت یا Javascript Environment می گوییم که مهم ترین آن مرورگر است .

شئ جاری در global scope بسته به همین محیط اجرا ممکن است متفاوت باشند. به طور مثال در مرورگر برابر است با BOM یا همان window و در سرور Nodejs برابر است با global .

strict mode

همان طور که پیش تر گفتیم شئ this در توابع در strict mode برابر undefined می باشد.

function foo(){
    "use strict"
    console.log(this)
}

Indirect Invoked (call,apply,bind)

همان طور که گفتیم در جاوا اسکریپت همه چیز شئ است . به طول مثال string , number, array , function شئ است . همان طول که گفتیم توابع هم شئ‌ هستند و می توان برای آن ها ویژگی و متد تعریف کرد.

سه متد اصلی توابع bind , call, apply می باشد.

bind

bind در جاوا اسکریپت بسیار معنی نزدیک به extends در php دارد به شکلی که this را در تابع به صورت دستی تعیین می کند.

var getName = function(){
    return this.name;
}
getName(); //""

var person = {
    name: 'Abolfazl',
}
var  newGetName = getName.bind(person)
newGetName(); //"Abolfazl"

در مثال بالا برای این که بتوانیم به متغیر های مورد نیاز در this دست پیدا کنیم person را به آن اضافه کردیم. راه دیگر bind به صورت کوتاه تر در مثال زیر مشاهده می کنید:

var person = {
    name: 'Abolfazl',
}
var getName = (function(){
    return this.name;
}).bind(person)
getName() //"Abolfazl"

مثال کاربردی تر برای این که یک متد را به عنوان callback به یک تابع دیگر ارسال می کنید( استفاده از Arrow functions هم در این مورد کاربردی است )

var employee = {
    name: 'Abolfazl',
    famil: 'sabagh',
    getName: function(){
        console.log(this.name + ' ' + this.famil)
    }
}
function sayWhoAreYou(callback){
    callback()
}
sayWhoAreYou(employee.getName)  //undefined
sayWhoAreYou(employee.getName.bind(employee)) //"Abolfazl sabagh"

نکته مهم : در Arrow Function موجودیت this به صورت lexically تعیین می شود یعنی اگر در جایی دیگر فراخوانی گردد از scope زمان تعریف گرفته می شود دقیقا مطابق با مثال بالا.

call

با استفاده از این متد علاوه برbind کردن شئ آن را فراخوانی نیز می کنیم. چون این متد تابع را فراخوانی می کند پس پارامتر های ورودی را نیز دریافت می کند.

تفاوت آن با bind این موارد است :

  • پارامتر نیز دریافت می کند
  • تابع را فراخوانی می کند برعکس که bind کپی از تابع را بر می گرداند.

در مثال زیر بدون استفاده از call متد را فراخوانی کنید مقدار خالی بر می گرداند چرا که this آن مقدار window است.

var person = {
    name: 'Abolfazl'
}
var getName = function(famil){
    console.log(this.name + ' ' +  famil )
}

getName.call(person,'sabagh') //"Abolfazl sabagh"

apply

apply دقیقا با همان هدف call فراخوانی می کند با این تفاوت که پارامتر ها را به صورت آرایه دریافت می کند . به مثلا در بلوک کد بالا برای فراخوانی با apply :

getName.apply(person,['sabagh'])
Abolfazl sabagh

 

مطالب مشابه

Obeject Data Structure in JavaScript

هر زبان برنامه نویسی از دو ساختار اصلی تشکیل شده است . بخش اول (Data Structure) ساختمان های داده آن و بخش دوم لیست...

Math and Arithmetic logic in JavaScript

اعداد در برنامه نویسی کاربردهای بسیار زیادی دارند. مهم ترین شناسه یک موجودیت یک عدد است که به آن Identifier می گوییم که...

اشتراک گذاری :

مدیر وب سایت گنوتک . برنامه نویسی رو با زبان C در هفده سالگی شروع کردم . در حال حاضر به برنامه نویسی php برپایه معماری MVC , HMVC و همچنین سیستم مدیریت محتوای WordPress و فریم ورک محبوب لاراول علاقه مند هستم و دوست دارم اطلاعاتم رو با شما به اشتراک بگذارم.

۰ دیدگاه برای توابع در جاوا اسکریپت (قسمت سوم)

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

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