传递参数
参数按值传递 并非按引用传递
function setName(obj) {
obj.name = "Nicholas";
}
let person = new Object();
setName(person);
console.log(person.name); // "Nicholas"
-----------------
function setName(obj) {
obj.name = "Nicholas";
obj = new Object();
obj.name = "Greg";
}
let person = new Object();
setName(person);
console.log(person.name); // "Nicholas"
个人理解 执行setName时 obj是在内存中的堆值 给这个值追加name属性后 重新给obj赋值 obj重新指向了一个新的堆地址 后续给obj新地址追加name属性 函数结束后这个新的obj被销毁 而person指向的obj原地址被添加了新属性
确定类型
typeof 只能确定字符串 数字 undefined 布尔值 instanceof通过原型链确定是objecrt array
性能
使用完后设置成null 让下次可以被垃圾回收
function createPerson(name){
let localPerson = new Object();
localPerson.name = name;
return localPerson;
}
let globalPerson = createPerson("Nicholas");
// 解除 globalPerson 对值的引用
globalPerson = null;
使用let const 以块(而非函数)为作用域,所以相比于使用 var,使用这两个新关键字可能会更早地让垃圾回 收程序介入,尽早回收应该回收的内存。在块作用域比函数作用域更早终止的情况下,这就有可能发生。
隐藏类
共享同一个构造函数和原型
function Article() {
this.title = 'Inauguration Ceremony Features Kazoo Band';
}
let a1 = new Article();
let a2 = new Article();
假如添加了这个
a2.author = 'Jake';
此时两个 Article 实例就会对应两个不同的隐藏类。根据这种操作的频率和隐藏类的大小,这有 可能对性能产生明显影响
“先创建再补充”(ready-fire-aim)式的动态属性赋值,并在 构造函数中一次性声明所有属性
function Article(opt_author) {
this.title = 'Inauguration Ceremony Features Kazoo Band';
this.author = opt_author;
}
let a1 = new Article();
let a2 = new Article('Jake');
使用delete
function Article() {
this.title = 'Inauguration Ceremony Features Kazoo Band';
this.author = 'Jake';
}
let a1 = new Article();
let a2 = new Article();
delete a1.author;
在代码结束后,即使两个实例使用了同一个构造函数,它们也不再共享一个隐藏类。动态删除属性 与动态添加属性导致的后果一样。最佳实践是把不想要的属性设置为 null。这样可以保持隐藏类不变 和继续共享,同时也能达到删除引用值供垃圾回收程序回收的效果
function Article() {
this.title = 'Inauguration Ceremony Features Kazoo Band';
this.author = 'Jake';
}
let a1 = new Article();
let a2 = new Article();
a1.author = null;
内存泄漏
自动声明导致被挂载到window上不会被回收
function setName() {
name = 'Jake';
}
定时器
let name = 'Jake';
setInterval(() => {
console.log(name);
}, 100);
闭包
let outer = function() {
let name = 'Jake';
return function() {
return name;
};
};