ວິຊາຂອບເຂດບັນຊີ ECMAScript

作用域指的是变量的适用范围。

公用、私有和受保护作用域

概念

在传统的面向对象程序设计中,主要关注于公用和私有作用域。公用作用域中的对象属性可以从对象外部访问,即开发者创建对象的实例后,就可使用它的公用属性。而私有作用域中的属性只能在对象内部访问,即对于外部世界来说,这些属性并不存在。这意味着如果类定义了私有属性和方法,则它的子类也不能访问这些属性和方法。

受保护作用域也是用于定义私有的属性和方法,只是这些属性和方法还能被其子类访问。

ECMAScript 只有公用作用域

对 ECMAScript 讨论上面这些作用域几乎毫无意义,因为 ECMAScript 中只存在一种作用域 - 公用作用域。ECMAScript 中的所有对象的所有属性和方法都是公用的。因此,定义自己的类和对象时,必须格外小心。记住,所有属性和方法默认都是公用的!

建议性的解决方法

许多开发者都在网上提出了有效的属性作用域模式,解决了 ECMAScript 的这种问题。

由于缺少私有作用域,开发者确定了一个规约,说明哪些属性和方法应该被看做私有的。这种规约规定在属性前后加下划线:

obj._color_ = "blue";

这段代码中,属性 color 是私有的。注意,下划线并不改变属性是公用属性的事实,它只是告诉其他开发者,应该把该属性看作私有的。

有些开发者还喜欢用单下划线说明私有成员,例如:obj._color。

静态作用域

ການຄວາມກຳນົດສະຖານະນະບັນດາສະໝອງສະເໜີບັນດາຄວາມແລະກົນລະຍຸດທີ່ສາມາດເຂົ້າເຖິງທັງໝົດທີ່ບໍ່ຈະສ້າງບັນດາສະໝອ�ຂອງປະເພດອອກແບບ, ເຊັ່ນ: java.net.URLEncoder ປະເພດອອກແບບ, ກົນລະຍຸດ encode() ຂອງປະເພດອອກແບບນີ້ແມ່ນກົນລະຍຸດສະຖານະນະບັນດາສະໝອງ.

ECMAScript ບໍ່ມີການຄວາມກຳນົດສະຖານະນະບັນດາສະໝອງ

ບໍ່ສາມາດຈະກ່າວວ່າ ECMAScript ບໍ່ມີການຄວາມກຳນົດສະຖານະນະບັນດາສະໝອງ. ແຕ່ວ່າມັນສາມາດສະໜອງບັນດາຄວາມແລະກົນລະຍຸດໃຫ້ການຈັດການສ້າງບັນດາສະໝອ�. ເບິ່ງອີກວ່າ, ການຈັດການສ້າງບັນດາສະໝອ�ພຽງແຕ່ກົນລະຍຸດ. ກົນລະຍຸດແມ່ນບັນດາສະໝອງ, ບັນດາສະໝອງແມ່ນບັນດາສະໝອ�, ບັນດາສະໝອ�ສາມາດມີບັນດາຄວາມແລະກົນລະຍຸດ. ເວລານັ້ນ, ການຈັດການສ້າງບັນດາສະໝອ�ພຽງແຕ່ກົນລະຍຸດ.

function sayHello() {
  alert("hello");
}
sayHello.alternate = function() {
  alert("hi");
}
sayHello(); // ອອກ "hello"
sayHello.alternate(); // ອອກ "hi"

TIY

ໃນການນີ້, ກົນລະຍຸດ alternate() ຂອງ sayHello() ແມ່ນບັນດາສະໝອງຂອງຫົວວິທະຍາ sayHello. ທ່ານສາມາດເອິ້ນ sayHello() ຄືກັບກົນລະຍຸດປົກກະຕິຂອງຫົວວິທະຍາ, ເພື່ອອອກ "hello", ຫຼືເອິ້ນ sayHello.alternate() ເພື່ອອອກ "hi". ແຕ່ວ່າ alternate() ກໍ່ແມ່ນບັນດາສະໝອງທີ່ຕິດຕາມຫົວວິທະຍາ sayHello() ໃນການໃຊ້ອິດສະຫຼະກຳ, ບໍ່ແມ່ນກົນລະຍຸດສະຖານະນະບັນດາສະໝອງ.

ສະເພາະສັບພີມ this

ການໃຊ້ສະເພາະສັບພີມ this

ໃນ ECMAScript, ໜຶ່ງໃນຄວາມຄິດທີ່ສຳຄັນທີ່ທ່ານຕ້ອງຮຽນຢູ່ແມ່ນການໃຊ້ສະເພາະສັບພີມ this. ສະເພາະສັບພີມ this ເປັນບັນດາສະໝອງຂອງບັນດາສະໝອ�. ສະເພາະສັບພີມ this ຈະຍິນວ່າບັນດາສະໝອ�ທີ່ຫາກຮັບຂໍ້ກຳນົດ, ເຊັ່ນ:

var oCar = new Object;
oCar.color = "red";
oCar.showColor = function() {
  alert(this.color);
};
oCar.showColor(); // ອອກ "red"

TIY

ໃນການຫົວຂໍ້ທີ່ວ່າ, ສະເພາະສັບພີມ this ນຳໃຊ້ໃນເຫດການ showColor() ຂອງບັນດາສະໝອງ. ໃນການເລື່ອງນີ້, this ແມ່ນ oCar. ການຫົວຂໍ້ທີ່ຫຼັງຈາກນັ້ນດຽວກັນກັບການຫົວຂໍ້ທີ່ກ່າວຂ້ອຍນີ້ກຳນົດບັນດາຄວາມທີ່ດຽວກັນ:

var oCar = new Object;
oCar.color = "red";
oCar.showColor = function() {
  alert(oCar.color);
};
oCar.showColor(); // ອອກ "red"

TIY

ການໃຊ້ this

ວ່າເປັນຫຍັງຈະໃຊ້ this? ຍ້ອນວ່າບໍ່ສາມາດຄາດໄດ້ວ່ານັກພັດທະນາຈະໃຊ້ຊື່ສານວິທະຍາໃດ. ພາຍໃນການໃຊ້ this, ທ່ານສາມາດນຳໃຊ້ຫົວວິທະຍາດຽວໃນຫຼາຍເຂດ. ການພິຈາລະນາຫຍັງພວກນີ້:

function showColor() {
  alert(this.color);
};
var oCar1 = new Object;
oCar1.color = "red";
oCar1.showColor = showColor;
var oCar2 = new Object;
oCar2.color = "blue";
oCar2.showColor = showColor;
oCar1.showColor();		//ສະແດງ "red"
oCar2.showColor();		//ສະແດງ "blue"

TIY

ໃນລະບັນຍັດດ້ານລຸ່ມນີ້, ກໍາລັງອະທິບາຍພັດທະນາ showColor() ກ່ອນໃສ່ສ້າງສອງໂອບຄອມ (oCar1 ແລະ oCar2), ໜຶ່ງໂອບຄອມມີຂໍ້ມູນ color ທີ່ "red", ໜຶ່ງໂອບຄອມມີຂໍ້ມູນ color ທີ່ "blue". ສອງໂອບຄອມທັງສອງມີຂໍ້ມູນ showColor, ທີ່ຍິງໄປຫາພັດທະນາ showColor() ດິງລະບຸວ່າບໍ່ມີບັນຫາຊື່ (ຍ້ອນວ່າໜຶ່ງແມ່ນພັດທະນາທົ່ວໄປ, ແລະໜຶ່ງແມ່ນຂໍ້ມູນຂອງໂອບຄອມ). ການເອິ້ນ showColor() ຂອງໂອບຄອມແຕ່ລະຫົວປະກອບ, oCar1 ຈະສະແດງ "red", ແລະ oCar2 ຈະສະແດງ "blue". ຍ້ອນວ່າການເອິ້ນ oCar1.showColor() ຈະເຮັດໃຫ້ສິດຫົວປະກອບ this ໃນພັດທະນາ ບັງຄັບໃຫ້ມີວ່າ oCar1. ການເອິ້ນ oCar2.showColor() ຈະເຮັດໃຫ້ສິດຫົວປະກອບ this ໃນພັດທະນາ ບັງຄັບໃຫ້ມີວ່າ oCar2.

ເວົ້າແມ່ນວ່າ, ເມື່ອອະທິບາຍຂອງໂອບຄອມ ຕ້ອງໃຊ້ສິດຫົວປະກອບ this. ເອງວ່າ, ຖ້າໃຊ້ລະບັນຍັດດ້ານລຸ່ມນີ້, showColor() ບໍ່ສາມາດໃຊ້ໄດ້:

function showColor() {
  alert(color);
};

ຖ້າບໍ່ໃຊ້ໂອບຄອມ ຫຼື ສິດຫົວປະກອບ this ໃຊ້ທີ່ພັດທະນາ ECMAScript ຈະຮັບມາວ່າພັດທະນາບໍ່ມີຫົວປະກອບທີ່ບໍ່ມີຊື່. ໃນຕອນນັ້ນ ພັດທະນາຈະຊອກຫາພັດທະນາທີ່ມີຊື່ color ທີ່ພັດທະນາທີ່ພາຍໃນຫຼັງ ແຕ່ບໍ່ສາມາດຫາໄດ້. ທີ່ຈະເກີດຫຍັງ? ພັດທະນາຈະສະແດງ "null" ໃນຄໍາເຕືອນ.