为什么我的对象不是私人的,当我的变量是?
我试图让一个对象是私人的,但不知道如何做到这一点。正如你所看到的名称变量是私有的,我不能编辑它,但是当涉及到我返回的对象时,我可以编辑它。不过,我不希望这是可能的。 在JavaScript中我很新的面向对象和私有方法,所以有人可以告诉我什么是对的和在这里。 :)我该如何解决这个问题? 谢谢!为什么我的对象不是私人的,当我的变量是?
var User = function() {
var name = 'bob';
this.getName = function() {
return name;
}
var otherInfo = {
age: 20,
human: true,
}
this.getOther = function() {
return otherInfo;
}
}
var person = new User();
var name = person.getName();
name = 'jenny';
console.log(person.getName()); // bob
var other = person.getOther();
other.age = 'wtf?';
console.log(person.getOther()); // { age: 'wtf?', human: true }
这是发生,因为在JS对象通过链接 - 没有从源对象coped。
刚刚尝试复制对象:
如字符串var User = function() {
var name = 'bob';
this.getName = function() {
return name;
}
var otherInfo = {
age: 20,
human: true,
}
this.getOther = function() {
return Object.assign({}, otherInfo);
}
}
var person = new User();
var name = person.getName();
name = 'jenny';
console.log(person.getName()); // bob
var other = person.getOther();
other.age = 'wtf?';
console.log(person.getOther()); // { age: 20, human: true }
这并不是真正的复制对象。相反,它使用'this.otherInfo'作为新对象的原型。 – forgivenson
好的。它是不同的快速答案。我将其更改为Object.assign –
您的代码仍然无法使用。测试一下。 – forgivenson
原始值按值传递。这意味着当您将一个字符串分配给您的变量时,您将该字符串的实际值设置为该变量。
对象是通过引用传递。这意味着当您将一个对象分配给您的变量时,您只需将对象的引用,而不是它的实际值。如果您有一个对象并将其分配给6个不同的变量,则每个变量将具有对同一个基础对象的引用。
在您的示例中,您的getOther
方法正在将参考返回到otherInfo
对象。所以,当你将age
属性设置为“wtf”时,你将它设置在你的变量引用的对象上。
您还声明var name
两次。
当您在用户功能的范围内声明var person = new User();
a var name
时。
当你var name = person.getName();
你声明一个变量具有相同的名称超出了用户功能的范围。
因此,当您name = 'Jenny';
解释器将此字符串name
变量关联到用户范围之外。
一般来说,将通用名称(名称,标题,ID,...)这样的变量用作全局变量是一个坏主意。我将使用this.
来引用对象属性,并定义setters
以及getters
。您也可以忽略setters
并参照用户属性与person.
,像这样:
function User() {
this.name = 'bob';
this.getName = function() {
return this.name;
}
this.otherInfo = {
age: 20,
human: true,
}
this.getOther = function() {
return this.otherInfo;
}
}
var person = new User();
console.log(person.getName()); // bob
person.name = 'jenny';
console.log(person.getName()); // jenny
console.log(person.getOther(); // { age: 20, human: true }
person.otherInfo.age = 'wtf?';
console.log(person.getOther()); // { age: 'wtf?', human: true }
您不必在Javascript对象范围“私人”的事情。从外部隐藏事物的唯一方法是使用函数范围,就像您使用name
(函数User
中的局部变量)所做的那样。
要每次返回一个内容相同的对象,可以在该函数内部创建该对象。与此类似,比如:
this.getOther = function() {
var otherInfo = {
age: 20,
human: true,
}
return otherInfo;
}
或者只是:
this.getOther = function() {
return {
age: 20,
human: true,
};
}
在这两种情况下,您将创建与每个调用一个新的对象。
如果您不想更改'person.getOther()'的返回值来更改'otherInfo'的值,那么您需要返回它的一个副本。 – forgivenson
我该怎么做? –
http://stackoverflow.com/questions/728360/most-elegant-way-to-clone-a-javascript-object – Jonathan