返回变量作为构造函数
Returning a variable as a constructor function
我是 JavaScript 的新手,有人建议我阅读《学习 JavaScript 设计模式》一书。我正在阅读工厂设计模式,遇到了以下困难,请看下面的脚本:
// Types.js - Constructors used behind the scenes
// A constructor for defining new cars
function Car( options ) {
// some defaults
this.doors = options.doors || 4;
this.state = options.state || "brand new";
this.color = options.color || "silver";
}
// A constructor for defining new trucks
function Truck( options){
this.state = options.state || "used";
this.wheelSize = options.wheelSize || "large";
this.color = options.color || "blue";
}
// FactoryExample.js
// Define a skeleton vehicle factory
function VehicleFactory() {}
// Define the prototypes and utilities for this factory
// Our default vehicleClass is Car
VehicleFactory.prototype.vehicleClass = Car;
// Our Factory method for creating new Vehicle instances
VehicleFactory.prototype.createVehicle = function ( options ) {
switch(options.vehicleType){
case "car":
this.vehicleClass = Car;
break;
case "truck":
this.vehicleClass = Truck;
break;
//defaults to VehicleFactory.prototype.vehicleClass (Car)
}
return new this.vehicleClass( options );
};
// Create an instance of our factory that makes cars
var carFactory = new VehicleFactory();
var car = carFactory.createVehicle( {
vehicleType: "car",
color: "yellow",
doors: 6 });
// Test to confirm our car was created using the vehicleClass/prototype Car
// Outputs: true
console.log( car instanceof Car );
// Outputs: Car object of color "yellow", doors: 6 in a "brand new" state
console.log( car );
这是我为工厂设计模式找到的示例,现在我的问题是理解以下行。考虑到车辆类被定义为一个变量:
VehicleFactory.prototype.vehicleClass = Car;
我不明白它作为构造函数返回:
return new this.vehicleClass( options );
好吧,这是我唯一的困难,一次又一次地运行代码,对我来说仍然没有意义。
这里返回的不是函数(你是对的,它没有意义)。返回的是一个新对象(请参阅 new
关键字)。
当您想要返回类型为 Truck
的新对象时,您将使用以下代码:
return new Truck( options )
但是,在这种特定情况下,您想要的车辆类型由用户定义。因此,this.vehicleClass
是指在返回值正上方的开关中定义的值。换句话说,vehicleClass
将被替换为Car
(或 Truck
),如果用户选择了car
(或 Truck
)。
因此,将调用的构造函数将是代码第一行中定义的Car
或Truck
构造函数。
我希望现在更清楚了。
您分配给VehicleFactory.prototype.vehicleClass
的不是实际的class
,而是对constructor function
的引用。
要在 JavaScript 中创建对象,new 运算符后必须跟一个构造函数。由于 VehicleFactory.prototype.vehicleClass
或稍后的代码 this.vehicleClass
中保存对构造函数的引用,因此您可以使用 new this.vehicleClass(options)
创建新的车辆对象。
JavaScript 的一大优点是能够将函数作为参数传递,而无需委托。
我希望这能让它更清楚一点。
问候
在Javascript中,函数是对象,因此它们可以用作返回值。这意味着函数不需要返回某种数据值或数据数组作为其执行的结果。
一个函数可以返回另一个更专业的函数,也可以按需创建另一个函数,具体取决于某些输入。下面是一个简单的示例:一个函数执行一些工作,可能是一些一次性初始化,然后处理其返回值。返回值恰好是另一个函数,也可以执行:
var setup = function () {
alert(1);
return function () {
alert(2);
};
};
// using the setup function
var my = setup(); // alerts 1
my(); // alerts 2
因为 setup() 包装了返回的函数,所以它会创建一个闭包,你可以使用这个闭包来存储一些私有数据,这些数据可以由返回的函数访问,但不能由外部代码访问。例如,一个计数器,每次调用它时都会为您提供一个递增的值:
var setup = function () {
var count = 0;
return function () {
return (count += 1);
};
};
// usage
var next = setup();
next(); // returns 1
资料来源:Stoyan Stefanov 的 JavaScript Patterns。
在您的情况下return new this.vehicleClass( options );
,正在返回一个新对象 调用构造函数 vehicleClass
.
new <expression>(<arguments>)
评估如下:
- 评估
<expression>
- 呼叫
new <result of 1>(<arguments>)
也就是说,您可以将任何表达式放在new
和左括号之间,只要此表达式返回函数即可。
顺便说一句,这段代码似乎没有以正确的方式做事。首先,它在原型上定义一个属性:
VehicleFactory.prototype.vehicleClass = Car;
然后,在 createVehicle
中,它添加一个具有相同名称的本地属性:
this.vehicleClass = Car;
这在后续查找中有效地覆盖了prototype
的vehicleClass
:
a = createVehicle(); // no `vehicleType` here, returns `Car`
b = createVehicle({vehicleType: 'truck'}); // returns `Truck`
c = createVehicle(); // no `vehicleType` here, but this time it returns `Truck`???
设计createVehicle
的更好方法是这样的:
VehicleFactory.prototype.createVehicle = function ( options ) {
var klass;
switch(options.vehicleType){
case "car":
klass = Car;
break;
case "truck":
klass = Truck;
break;
}
return new (klass || this.vehicleClass)( options );
};
主观地说,"设计模式"在javascript中并不是很惯用,如果你想要另一个阅读建议,试试JavaScript Allongé。
- 构造函数函数闭包变量
- 正在向构造函数添加作用域变量
- 尝试将变量传递到对象中时的作用域问题'的方法构造函数
- 返回变量作为构造函数
- “var”变量,“this”变量和“global”变量 - 在JavaScript构造函数中
- JavaScript 构造函数中的“var”变量会发生什么
- 在 promise 中获取构造函数变量
- 是否需要初始化在 Javascript 中作为“类”构造函数参数传递的变量
- 在实例化期间使用构造函数变量
- 角度表达式无法使用构造函数属性分辨变量类型
- 使用类/构造函数与变量方法时的作用域不同
- 如何在嵌套原型中访问 JavaScript 构造函数变量
- 如何访问构造函数变量
- JavaScript:在构造函数中使用原型函数更改变量
- 从构造函数变量内部调用函数,在 JavaScript 中给出 Undefiend 错误
- 为什么我在构造函数中附加“this”的变量会失去其绑定
- 使用 JavaScript 和构造函数的动态变量名称:使用 EaselJS 将图像动态克隆到多个画布
- 如何使用在构造函数中创建的方法更新同一构造函数中的另一个变量
- Javascript-Prototype没有读取构造函数变量
- 打印构造函数变量的名称