我在typescript中添加了以下类
class Person {
private variable1;
public varibele2;
Person(){
this.variable1 = 'abc';
this.varibele2 = 'xyz';
}
public getVariable1(){
return this.variable1;
}
}
所以当我使用tsc编译代码时,它会生成以下代码
var Person = (function () {
function Person() {
}
Person.prototype.Person = function () {
this.variable1 = 'abc';
this.varibele2 = 'xyz';
};
Person.prototype.getVariable1 = function () {
return this.variable1;
};
return Person;
}());
由于variable1是私有的,因此该类的obj无法访问(在typescript代码中发生)。
同样的行为应该发生在已编译的es5代码中(但不会发生)。
在上面示例的已编译代码中,我创建了Person的对象
var p = new Person();
console.log(p.variable1); // undefined
p.variable1 = 'abc1'; // setting value to variable 1
console.log(p.variable1); // 'abc1'
console.log(p.getVariable1()); // 'abc1'
在上面的代码中,我不能设置或获取variable1的值。
var p = new Person();
console.log(p.getVariable1()); // 'undefined'
p.variable1 = 'abc1'; // setting value to variable1
console.log(p.getVariable1()); // 'abc1'
在上面的代码中,我尝试使用p.getVariable1()获取值,并且我得到undefined。因为值已经在类的构造函数中分配,所以它应该可以通过p.getVariable1()
获得var p = new Person();
console.log(p.variable2); // undefined
p.variable2 = 'xyz1'; // setting value
console.log(p.variable2);// 'xyz1'
在上面的代码中,Variable2应该重新启动' xyz'但事实并非如此。一旦我为它赋值,它就会返回。
因此私有和公共变量的行为在转换代码中是相同的,并且非常令人困惑。 它不返回在构造函数中赋值的值。
答案 0 :(得分:2)
要继续我们对评论的讨论,以下是使用公共与私有的好处:
IDE会立即告诉您,您正在做一些您不应该做的事情。如果您忽略这些错误,代码将编译为javascript并运行,但关键是您不忽略这些错误。当您编写这样的错误代码时,typescript会告诉您存在问题,然后您可以解决问题。如果您有构建过程,则可以对其进行设置,以便这些打字错误将使构建失败,从而迫使您在部署之前解决问题。
Typescript是一个工具,通过更早,更容易地捕获错误,帮助您编写更好的JavaScript代码。它不是改变javascript工作方式的工具。 Typescript不提供运行时类型检查,如果这就是你所追求的,你就找不到它。如果你需要闭包来隐藏变量,那么自己创建一个闭包。
答案 1 :(得分:1)
首先,回答你的主要问题:
为什么类中的私有变量在转换后的代码中被视为公共。
private
属性以及readonly
属性确实被转换为普通属性,因此是“公共”属性。我认为这是为了简化和增强转换TS→JS并支持在任何地方使用TypeScript,在对这些属性执行无效操作时会发出警告或错误:访问类外的私有属性,重新分配只读属性... < / p>
但是你给出的例子有非常奇怪的行为。它们不是由于TypeScript转换。我注意到你的班级人员遇到了一些问题:
constructor
定义的,而不是类名。它更令人困惑,因为构造函数被转换为一个名为类的函数构造函数,这里是Person
。varibele2
而不是variable2
。这就是console.log(p.variable2)
无法打印预期值的原因。修复这些问题,代码的行为更具逻辑性。
class Person {
constructor(private _variable1 = 'abc', public variable2 = 'xyz') { }
public get variable1() { return this._variable1; }
}
console.log(new Person()); // → Person { v1: [Getter], v2: "xyz", _v1: "abc", __proto__... }
通过TypeScript playground可以获得已编译的代码。
注意:我赞成另一种语法:
_x
,以便于编写getter get x() { return this._x; }
。它也是一种常用的JavaScript约定,表明该变量是私有的,没有复杂的模式来真正拥有私有属性。答案 2 :(得分:0)
根据我的理解,在以下情况中,变量2未定义,因为对象p不包含该变量。
在下面的代码中,我们使用p.variable2 ='xyz1'将变量包含到对象p中。所以在第三行我们得到该变量的值。
var p = new Person();
console.log(p.variable2); // undefined
p.variable2 = 'xyz1'; // setting value
console.log(p.variable2);// 'xyz1'
还有问题是,因为typescript已经声明了变量,那么为什么javascript(编译代码)对象不包含那些变量?
答案 3 :(得分:0)
如果转译的代码没有使用闭包将其设为私有,这意味着我可以在将其用作javascript库时摆弄变量,因为我永远不会知道私有是什么。因此,答案是转换打字稿的方式是不正确的,并且不是真正使用javascript的精神。