tips1.继承方式
- 1原始继承方式
Event.prototype.say = function() {
console.log('say');
}
function Event() {
var a = 10;
this.type = 'function';
}
Http.prototype = new Event();
function Http() {
}
var oHttp = new Http();
console.log(oHttp.type);
- 过多的继承无用的属性
- 2.借用构造函数
function Person(name, age, sex) {
this.name = name;
this.age = age;
this.sex = sex;
}
var oPerson = new Person();
function Student(name, age, sex, grade, clas) {
// creative this {}
// this.name = name;
// this.age = age;
// this.sex = sex;
Person.call(this, name, age, sex);
this.grade = grade;
this.clas = clas;
//return this;
}
var oStudent = new Student('yp', 18, 'man', 3, 3);
- 不能继承借用构造函数的原型
- 每次构造函数都要多走一个函数
- 3共享原型
Event.prototype.say = function() {
console.log('say');
}
Event.prototype.show = function(){
}
function Event() {
var a = 10;
this.type = 'function';
this.show();
}
Http.prototype = Event.prototype;
Http.prototype.show = function(){
}
function Http() {
}
var oHttp = new Http();
console.log(oHttp.type);
- 虽然不会继承多余属性
- 但是由于对象是引用值,因此下游改变会影响上游
- 4圣杯模式
Father.prototype.lastName = 'Deng';
function Father() {
}
function Son() {
this.girlFriend = 'ab';
}
Event.prototype.say = function() {}
function Event() {
}
function Http() {
this.status = 200;
}
var inherit = (function() {
var Cache = function() {
//生成闭包
};
return function(Target, Origin) {
Cache.prototype = Origin.prototype;
Target.prototype = new Cache();
Target.prototype.constructor = Target;
Target.prototype.uber = Origin;
}
})();
inherit(Son, Father);
inherit(Http, Event);
tips2.命名空间
- 管理变量, 防止污染全局, 适用于模块化开发
- 命名空间已经不使用
- 防止代码污染 有效方式: 立即执行函数, 封闭作用域
(function() {
var message = 'red div';
topDiv.onclick = function() {
alert(message);
}
})();
tips3.链式调用
var mrDeng = {
health: 100,
smoke: function() {
this.health -= 5;
return this;
},
drink: function() {
this.health -= 4;
return this;
},
perm: function() {
this.health += 2;
return this;
}
}
mrDeng.smoke().drink().perm(); //链式调用
// 返回值.drink().perm();
// 我们返回一个对象,刷新后的mrDeng继续调用后面的方法 return (新的)this--(mrDeng)
- mrDeng是一个对象,然后链式的执行方法,其中的原理很简单,就是执行完一个方法之后就返回对象本身
var prop = 'wife1';
var mrDeng = {
wife1: 'xiao 1',
wife2: 'xiao 2',
wife3: 'xiao 3',
wife4: 'xiao 4',
sayWife: function() {
document.write('my wife' + this.prop);
}
};
mrDeng.sayWife();
- 输出结果是【my wifeundefined】
- this.prop 相当于 this[‘prop’]
- 对象内没有这个属性字符串
- this[prop]
var prop = 'wife1';
var mrDeng = {
wife1: 'xiao liu',
wife2: 'xiao wang',
wife3: 'xiao lang',
wife4: 'xiao gei',
saywife: function(num) {
// document.write('我的老婆是' + this['wife' + num]);
//mrDeng.wife2 -> mrDeng['wife2'] this.wife2 -> this['wife2']
document.write('我的老婆是' + this.prop);
document.write('我的老婆是' + this['prop']);
//this.prop -> this['prop'] 字符串prop和变量prop
document.write('我的老婆是' + this[prop]);
}
}
mrDeng.saywife(3);
tips4.对象枚举
- for _ in _ (枚举遍历所有属性)
var mrDeng = {
son: 'mini Deng',
wife: 'miss liu',
age: 40,
sex: 'male',
__proto__: {
company: 'DUYI',
car: 'oooo'
}
}
for (var prop in mrDeng) {
console.log(prop);
console.log(prop, mrDeng[prop]);
}
- hasOwnProperty (判断是否是自己的属性)
var mrDeng = {
son: 'mini Deng',
wife: 'miss liu',
age: 40,
sex: 'male',
__proto__: {
company: 'DUYI',
car: 'oooo'
}
}
for (var prop in mrDeng) {
console.log(prop, mrDeng[prop], mrDeng.hasOwnProperty(prop));
- in(判断是否是自己以及原型链中的属性)
var mrDeng = {
son: 'mini Deng',
wife: 'miss liu',
age: 40,
sex: 'male',
__proto__: {
company: 'DUYI',
car: 'oooo'
}
}
for (var prop in mrDeng) {
console.log(prop in mrDeng);
}
- instanceof(看一下A的原型链上有没有B的原型)
function A() {
}
var oA = new A();
console.log(oA instanceof A);
var b = [];
console.log(b.constructor);
console.log(b instanceof Array);
console.log(b instanceof Object);
// A(对象的原型链上) instanceof(有没有) B(构造函数的原型)
// 看一下A的原型链上有没有B的原型
// 跨域不适用
- caller & callee
- caller(调用者)返回一个函数的引用,这个函数调用了当前的函数;
- callee放回正在执行的函数本身的引用,它是arguments的一个属性
var num = (function(n) {
if (n == 1 || n == 2) {
return 1;
}
return arguments.callee(n - 1) + arguments.callee(n - 2);
})(7);
- 递归
tips5.克隆
- 浅层克隆
var mrChen = {
name: 'cst',
age: 18,
sex: 'man',
girlFriend: {
name: 'zly',
age: 28
},
height: 183
}
var obj = {};
function clone(target, origin) {
for (var prop in origin) {
target[prop] = origin[prop];
}
}
clone(obj, mrChen);
obj.girlFriend.name = 'zzt';
//这种克隆存在弊端。原始对象的引用值地址给了克隆体,克隆体改变值会影响原始值
-
深层克隆
1.判断是不是原始值,如果是引用值,地址给了你,大家都可以改变
2.判断是数组还是对象
3.如果是建立在相应的数组或对象 反之直接copy
4.如果上述建立了数组或对象,对此我们再次深度拷贝
var mrChen = {
name: 'cst',
age: 18,
sex: 'man',
girlFriend: {
name: 'zly',
age: 28
},
height: 183
}
var obj = {};
function clone(target, origin) {
var str = '[object Array]'; //判断是不是数组的关键字
var toString = Object.prototype.toString; //如果经常使用某一个方法可以使用简单的变量名去储存
for (var prop in origin) {
if (origin.hasOwnProperty(prop)) {
//是不是自己的属性,不想要原型链上的属性
if (typeof origin[prop] == 'object') {
//判断这个值是不是对象或数组
if (toString.call(origin[prop]) === str) {
//判断是不是数组
target[prop] = [];
//你是数组,先给你一个数组的外壳,你是引用值不能把地址直接给你,
//我用递归把你属性中属性值是数组、对象的属性再次循环判断
//将其中的值赋给克隆体,给外壳加料
} else {
target[prop] = {};//后面把值给他
}
clone(target[prop], origin[prop]);
//递归,将属性中对象的值赋给它
} else {
target[prop] = origin[prop]//原始值直接赋值
}
}
}
}
clone(obj, mrChen);
obj.girlFriend.name = 'zzh';
- 纯函数(pure function):纯函数是指不依赖于且不改变它作用域之外的变量状态的函数。
也就是说,纯函数的返回值只由它调用时的参数决定,
它的执行不依赖于系统的状态(比如:何时、何处调用它——译者注)。
----------------------------------------------------------------------------------------------------------------------------------------
----------------------------------------------------------------------------------------------------------------------------------------
- 判断一个对象是不是数组的方法
var a = [];
1. Object.prototype.
toString
.call(a); 2. a
instanceof
Array; 3. a.
consturctor
tips6.this
- 普通函数
function test(a) {
//AO {a:44, b:undefined, c:function(){}, this:window}
console.log(this);
//没有任何显示调用,那么this就是window,可以输出
var b = 10;
function c() {
}
var c = 20;
}
test(44); //window
- 一个对象的属性
var obj = {
show: function test(a) {
//AO {a:44, b:undefined, c:function(){}, this:obj}
console.log(this);
var b = 10;
function c() {
}
var c = 20;
},
name: 'yp'
}
obj.show(44); //obj
- 构造函数
function test(a) {
//AO {a:44, b:undefined, c:function(){}, this:Object.create(test.prototype)}
//var this = Object.create(test.prototype);
console.log(this);
var b = 10;
function c() {
}
var c = 20;
}
var b = new test(); //Object.create(test.prototype)
//this 是个 对象 原型是test.prototype