关于深浅 拷贝
2017-09-20 本文已影响16人
black白先森
浅拷贝
function extend(parent, child) {
var i;
child = child || {};
for (i in parent) {
if (parent.hasOwnProperty(i)) {
child[i] = parent[i];
}
}
return child;
}
深拷贝
所有你需要做的事情只是检查一个属性的类型是否是对象,如果是,则递归遍历它的属性。另外一个需要做的检查是这个对象是真的对象还是数组
function extendDeep(parent, child) {
var i,
toStr = Object.prototype.toString,
astr = "[object Array]";
child = child || {};
for (i in parent) {
if (parent.hasOwnProperty(i)) {
if (typeof parent[i] === "object") {
child[i] = (toStr.call(parent[i]) === astr) ? [] : {};
extendDeep(parent[i], child[i]);
} else {
child[i] = parent[i];
}
}
}
return child;
}
var dad = {
counts: [1, 2, 3],
reads: {paper: true}
};
var kid = extendDeep(dad);
kid.counts.push(4);
kid.counts.toString(); // "1,2,3,4"
dad.counts.toString(); // "1,2,3"
dad.reads === kid.reads; // false
kid.reads.paper = false;
kid.reads.web = true;
dad.reads.paper; // true
混元(Mix-ins)
你还可以从任意多数量的对象中复制属性,然后将它们混在一起组成一个新对象
function mix() {
var arg, prop, child = {};
for (arg = 0; arg < arguments.length; arg += 1) {
for (prop in arguments[arg]) {
if (arguments[arg].hasOwnProperty(prop)) {
child[prop] = arguments[arg][prop];
}
}
}
return child;
}
var cake = mix(
{eggs: 2, large: true},
{butter: 1, salted: true},
{flour: "3 cups"},
{sugar: "sure!"}
);
借用函数 比较常用
你希望使用某个已存在的对象的一两个方法,你希望能复用它们,但是又真的不希望和那个对象产生继承关系,因为你只希望使用你需要的那一两个方法,而不继承那些你永远用不到的方法
// 一个简单实现绑定的函数
function bind(o, m) {
return function () {
return m.apply(o, [].slice.call(arguments));
};
}
// eg:
var cc = bind(3,back)();
console.log(cc); // 6
// ES5 中已经有 Function.prototype.bind(),不支持的环境实现
if (typeof Function.prototype.bind === "undefined") {
Function.prototype.bind = function (thisArg) {
var fn = this,
slice = Array.prototype.slice,
args = slice.call(arguments, 1);
return function () {
return fn.apply(thisArg, args.concat(slice.call(arguments)));
};
};
}
//call() example
notmyobj.doStuff.call(myobj, param1, p2, p3);
// apply() example
notmyobj.doStuff.apply(myobj, [param1, p2, p3]);
var obj = {
getA: function(){
return this + 10;
}
}
// 在js里面万物皆对象, String,Number,Boolean 是有基本包装对象的
var aa = obj.getA.call(1); // 11
console.log(aa)