我不知道最好的方法是创建具有属性和方法的JavaScript对象。
我看过一些示例,该示例中的人员使用var self = this然后self.在所有功能中使用以确保范围始终正确。
然后,我看到了.prototype用于添加属性的示例,而其他示例则是内联的。
有人可以给我一个带有某些属性和方法的JavaScript对象的正确示例吗?
我不知道最好的方法是创建具有属性和方法的JavaScript对象。
我看过一些示例,该示例中的人员使用var self = this然后self.在所有功能中使用以确保范围始终正确。
然后,我看到了.prototype用于添加属性的示例,而其他示例则是内联的。
有人可以给我一个带有某些属性和方法的JavaScript对象的正确示例吗?
Closure是多功能的。在创建对象时,bobince很好地总结了原型与封闭方法。但是,您可以模仿OOP以功能编程方式使用闭包的某些方面。记住函数是JavaScript中的对象 ; 因此以不同的方式将函数用作对象。
这是关闭的示例:
function outer(outerArg) {
return inner(innerArg) {
return innerArg + outerArg; //the scope chain is composed of innerArg and outerArg from the outer context
}
}
前一段时间,我碰到了Mozilla关于Closure的文章。这就是我的看法:“闭包可让您将某些数据(环境)与对该数据进行操作的函数相关联。这与面向对象编程(其中对象允许我们将某些数据(对象的属性)相关联”具有明显的相似之处。)使用一种或多种方法 ”。这是我第一次阅读闭包与经典OOP之间的并行性,而没有引用原型。
怎么样?
假设您要计算某些商品的增值税。增值税可能会在申请有效期内保持稳定。在OOP(伪代码)中执行此操作的一种方法:
public class Calculator {
public property VAT { get; private set; }
public Calculator(int vat) {
this.VAT = vat;
}
public int Calculate(int price) {
return price * this.VAT;
}
}
基本上,您将VAT值传递给构造函数,然后您的calculate方法可以通过闭包对其进行操作。现在,不使用类/构造函数,而是将VAT作为参数传递给函数。因为您唯一感兴趣的是计算本身,所以返回一个新函数,即calculate方法:
function calculator(vat) {
return function(item) {
return item * vat;
}
}
var calculate = calculator(1.10);
var jsBook = 100; //100$
calculate(jsBook); //110
在您的项目中,确定最适合用来计算增值税的顶级值。根据经验,每当您不断传递相同的参数时,就有一种使用闭包改进它的方法。无需创建传统对象。
https://developer.mozilla.org/zh-CN/docs/Web/JavaScript/Guide/Closures
除了2009年接受的答案。如果您可以针对现代浏览器,则可以使用Object.defineProperty。
Object.defineProperty()方法直接在对象上定义新属性,或修改对象上的现有属性,然后返回对象。资料来源:Mozilla
var Foo = (function () {
function Foo() {
this._bar = false;
}
Object.defineProperty(Foo.prototype, "bar", {
get: function () {
return this._bar;
},
set: function (theBar) {
this._bar = theBar;
},
enumerable: true,
configurable: true
});
Foo.prototype.toTest = function () {
alert("my value is " + this.bar);
};
return Foo;
}());
// test instance
var test = new Foo();
test.bar = true;
test.toTest();
要查看桌面和移动设备兼容性列表,请参见Mozilla的浏览器兼容性列表。是的,IE9 +和Safari移动版都支持它。
当在构造函数调用过程中使用关闭“ this”的技巧时,是为了编写一个函数,该函数可以被其他不想在该对象上调用方法的对象用作回调。它与“使范围正确”无关。
这是一个普通的JavaScript对象:
function MyThing(aParam) {
var myPrivateVariable = "squizzitch";
this.someProperty = aParam;
this.useMeAsACallback = function() {
console.log("Look, I have access to " + myPrivateVariable + "!");
}
}
// Every MyThing will get this method for free:
MyThing.prototype.someMethod = function() {
console.log(this.someProperty);
};
您可能会从阅读道格拉斯·克罗克福德(Douglas Crockford)关于JavaScript的内容中学到很多。约翰·雷西格(John Resig)也很聪明。祝好运!
在es6中,您现在可以实际创建一个 class
现在,您可以执行以下操作:
class Shape {
constructor(x, y) {
this.x = x;
this.y = y;
}
toString() {
return `Shape at ${this.x}, ${this.y}`;
}
}
因此,可以延伸到一个圆圈(如其他答案所示):
class Circle extends Shape {
constructor(x, y, r) {
super(x, y);
this.r = r;
}
toString() {
let shapeString = super.toString();
return `Circular ${shapeString} with radius ${this.r}`;
}
}
最终在es6中变得更干净,更易于阅读。
这是一个有效的例子:
class Shape {
constructor(x, y) {
this.x = x;
this.y = y;
}
toString() {
return `Shape at ${this.x}, ${this.y}`;
}
}
class Circle extends Shape {
constructor(x, y, r) {
super(x, y);
this.r = r;
}
toString() {
let shapeString = super.toString();
return `Circular ${shapeString} with radius ${this.r}`;
}
}
let c = new Circle(1, 2, 4);
console.log('' + c, c);
您也可以使用结构以这种方式进行操作:
function createCounter () {
var count = 0;
return {
increaseBy: function(nb) {
count += nb;
},
reset: function {
count = 0;
}
}
}
然后 :
var counter1 = createCounter();
counter1.increaseBy(4);
我相当频繁地使用此模式-我发现它在需要时为我提供了极大的灵活性。在使用中,它非常类似于Java风格的类。
var Foo = function()
{
var privateStaticMethod = function() {};
var privateStaticVariable = "foo";
var constructor = function Foo(foo, bar)
{
var privateMethod = function() {};
this.publicMethod = function() {};
};
constructor.publicStaticMethod = function() {};
return constructor;
}();
这将使用创建时调用的匿名函数,并返回一个新的构造函数。由于匿名函数仅被调用一次,因此您可以在其中创建私有静态变量(它们在闭包内部,对于该类的其他成员可见)。构造函数基本上是一个标准的Javascript对象-您在其中定义私有属性,并将公共属性附加到this变量中。
基本上,这种方法将Crockfordian方法与标准Javascript对象结合在一起,以创建功能更强大的类。
您可以像使用其他任何Javascript对象一样使用它:
Foo.publicStaticMethod(); //calling a static method
var test = new Foo(); //instantiation
test.publicMethod(); //calling a method
创建一个对象
在JavaScript中创建对象的最简单方法是使用以下语法:
这对于以结构化方式存储数据非常有用。
但是,对于更复杂的用例,通常最好创建函数实例:
这使您可以创建共享相同“蓝图”的多个对象,类似于您在例如中使用类的方式。Java。
但是,仍然可以通过使用原型来更高效地完成此操作。
每当函数的不同实例共享相同的方法或属性时,就可以将它们移至该对象的原型。这样,函数的每个实例都可以访问该方法或属性,但是不必为每个实例都复制它。
In our case, it makes sense to move the method
fto the prototype :Inheritance
A simple but effective way to do inheritance in JavaScript, is to use the following two-liner :
That is similar to doing this :
The main difference between both is that the constructor of
Ais not run when usingObject.create, which is more intuitive and more similar to class based inheritance.You can always choose to optionally run the constructor of
Awhen creating a new instance ofBby adding adding it to the constructor ofB:If you want to pass all arguments of
BtoA, you can also useFunction.prototype.apply():If you want to mixin another object into the constructor chain of
B, you can combineObject.createwithObject.assign:Demo
Note
Object.create可以在包括IE9 +在内的所有现代浏览器中安全使用。Object.assign不适用于任何版本的IE或某些移动浏览器。建议使用polyfillObject.create和/或Object.assign如果要使用它们并支持未实现它们的浏览器。你可以找到一个填充工具对
Object.create这里 和一个Object.assign在这里。