引用对象深度赋值

var cloneObj = function(obj){
    var str, newobj = obj.constructor === Array ? [] : {};
    if(typeof obj !== ‘object‘){
        return;
    } else if(window.JSON){
        str = JSON.stringify(obj), //系列化对象
        newobj = JSON.parse(str); //还原
    } else {
        for(var i in obj){
            newobj[i] = typeof obj[i] === ‘object‘ ?
            cloneObj(obj[i]) : obj[i];
        }
    }
    return newobj;
};

一、jQuery.merge( first, second )

first第一个用来合并的数组,元素是第二数组加进来的。 second第二个数组合并到第一,保持不变。$.merge()函数是破坏性的。它改变了从第二个添加项目到第一个参数。 如果您需要原始的第一个数组,请在调用$.merge()前拷贝一个出来。

var newArray = $.merge([], oldArray);
var first = [‘a‘,‘b‘,‘c‘];
var second = [‘d‘,‘e‘,‘f‘];
var result=$.merge( $.merge([],first), second);

function (first, second) {
    var l = second.length,
        i = first.length,
        j = 0;

    if (typeof l === "number") {
        for (; j < l; j++) {
            first[i++] = second[j];
        }

    } else {
        while (second[j] !== undefined) {
            first[i++] = second[j++];
        }
    }

    first.length = i;

    return first;
}

二、JavaScript concat() 方法

var aa = [].concat([12]),bb = [].concat([12]);
aa==bb//false

三、js对象浅拷贝,简单的赋值就是浅拷贝。因为对象和数组在赋值的时候都是引用传递。赋值的时候只是传递一个指针。

jQuery的API手册中,extend方法挂载在jQuery和jQuery.fn两个不同对象上方法,但在jQuery内部代码实现的是相同的,只是功能却不太一样

且看官方给出解释:

jQuery.extend(): Merge the contents of two or more objects together into the first object.(把两个或者更多的对象合并到第一个当中);

jQuery.fn.extend():Merge the contents of an object onto the jQuery prototype to provide new jQuery instance methods.(把对象挂载到jQuery的prototype属性,来扩展一个新的jQuery实例方法)

简单理解两者区别:

jQuery.extend(object); 为扩展jQuery类本身,为自身添加新的方法。

jQuery.fn.extend(object);给jQuery对象添加方法。

(1)  jQuery.extend( target [, object1 ] [, objectN ] )

合并object1, objectN到target对象,如果只有一个参数,则该target对象会被合并到jQuery对象中

var object1 = {apple: 0,banana: { weight: 52, price: 100 },cherry: 97};
var object2 = {banana: { price: 200 },durian: 100};
$.extend( object1);
$.extend( object1, object2 );

(2) jQuery.extend( [deep ], target, object1 [, objectN ] )

深度复制合并对象,第一个参数是boolean类型的true时,将object1, objectN深度复制后合并到target中;关于深度复制,是将除null, undefined,window对象,dom对象,通过继承创建的对象外的其它对象克隆后保存到target中;

深度与非深度复制区别是,深度复制的对象中如果有复杂属性值(如数组、函数、json对象等),那将会递归属性值的复制,合并后的对象修改属性值不影响原对象,如下面例子:

var obj1 = { a : ‘a‘, b : ‘b‘ };
var obj2 = {  x : { xxx : ‘xxx‘, yyy : ‘yyy‘ },  y : ‘y‘ };
 $.extend(true, obj1, obj2);
alert(obj1.x.xxx);  // 得到"xxx"
obj2.x.xxx = ‘zzz‘;          //修改obj2对象属性的内联值,不影响合并后对象obj1
alert(obj2.x.xxx); // 得到"zzz"
alert(obj1.x.xxx); // 得到"xxx"  //值保持;如果不加true,则得到“zzz”

(3)jQuery.fn.extend(object);

jQuery.fn = jQuery.prototype 即指向jQuery对象的原型链,对其它进行的扩展,作用在jQuery对象上面;一般用此方法来扩展jQuery的对象插件

//将hello方法合并到jquery的实例对象中。

$.fn.extend({
      hello:function(){alert(‘hello‘);}
});

//在jquery全局对象中扩展一个net命名空间。

$.extend($.net,{

     hello:function(){alert(‘hello‘);}

});  //使用jQuery.net.hello();

浅复制的实现

 $ = {
       extend : function(target, options) {
          for (name in options) {
              target[name] = options[name];
          }
          return target;
      }
  }; 

深复制的实现

$ = { 

     extend : function(deep, target, options) { 

          for (name in options) { 

              copy = options[name]; 

              if (deep && copy instanceof Array) { 

                  target[name] = $.extend(deep, [], copy); 

              } else if (deep && copy instanceof Object) { 

                  target[name] = $.extend(deep, {}, copy); 

              } else { 

                target[name] = options[name]; 

            } 

        } 

        return target; 

    }
}; 

四、jQuery.clone

$(selector).clone(includeEvents)   //includeEvents:可选。布尔值。规定是否复制元素的所有事件处理。默认地,副本中不包含事件处理器。

五、jQuery.map

$(‘:checkbox‘).map(function() {
  return this.id;
}).get().join(‘,‘);

由于返回值是 jQuery 封装的数组,使用 get() 来处理返回的对象以得到基础的数组。两种转换方式将一个jQuery对象转换成DOM对象:[index]和.get(index);

var arr1= [0,1,2];
var arr2=$.map( arr1, function(n){
return n;
});
console.log(arr1==arr2)//false

jQuery.map源码,return数组数据

function (elems, callback, arg) {
    var value, key, ret = [],
        i = 0,
        length = elems.length,
    // jquery objects are treated as arrays
    isArray = elems instanceof jQuery || length !== undefined && typeof length === "number" && ((length > 0 && elems[0] && elems[length - 1]) || length === 0 || jQuery.isArray(elems));

    // Go through the array, translating each of the items to their
    if (isArray) {
        for (; i < length; i++) {
            value = callback(elems[i], i, arg);

            if (value != null) {
                ret[ret.length] = value;
            }
        }

        // Go through every key on the object,
    } else {
        for (key in elems) {
            value = callback(elems[key], key, arg);

            if (value != null) {
                ret[ret.length] = value;
            }
        }
    }

    // Flatten any nested arrays
    return ret.concat.apply([], ret);
}
时间: 2024-12-30 06:55:29

引用对象深度赋值的相关文章

C++:对象的赋值和复制

3.6.1 对象赋值语句 如同基本类型赋值语句一样,同类型的对象之间也可以进行赋值,即一个对象的值可以赋给另一个对象.这里所指的对象的赋值是指对其中的数据成员赋值,而不对成员函数赋值.例如:A和B是同一类的两个对象,那么下述对象赋值语句 B=A: 就能把对象A的数据成员的值逐位复制给对象B //例3.24 对象赋值语句示例 #include<iostream> using namespace std; class Myclass{ public: void set(int i,int j) {

《Java开发手册》学习进程之对象引用与接口引用间的赋值和强制类型转换问题

对象引用之间: 子类引用可以赋值给父类引用. 父类引用需要在强制转换之后才能赋值给子类引用. 对于对象引用的强制转换,只要被转换的引用类型与转换后的目标类型之间是派生或被派生的关系,就可以通过编译.如果没有这些关系而去强制转换,则编译报错. 即使编译通过,如果被转换的引用指向的对象类型与转换后的目标类型之间不相符或不兼容(即被转换的引用指向的对象类型不能转换为除自身或者自身父类的其他类型,同下),则运行出错. 接口引用之间: 子接口引用可以赋值给父接口引用. 父接口引用需要在强制类型转换之后才能

Python中的变量引用对象需注意的几点

Python中的变量引用对象需注意的几点 分类:Python (55)  (0) 普通引用: Python中,变量的作用仅仅是一个标识,只有赋值后才被创建,它可以引用任何类型的对象,而且在引用之前必须赋值.赋值后的变量指向响应的对象,拥有该对象的空间.类型属于对象,但是不是变量. [python] view plain copy a = 3 a = "science" 上述代码说明数值3和字符串"science"分别是两种对象,初始变量a赋值对象3被创建,变量a指向

C++ 对象的赋值和复制 基本的

对象的赋值 如果对一个类定义了两个或多个对象,则这些对象之间是可以进行赋值,或者说,一个对象的值可以赋值给另一个同类的对象.这里所指的值是指对象中所有数       据的成员的值.对象之间进行赋值是“=”进行的,对象赋值的形式如下: 对象名1=对象名2; #include <iostream>using namespace std;class Box{public: Box(int =10,int =10,int =10); int volume();private: int height;

为什么类的拷贝构造参数加引用、重载赋值函数的返回值和参数加引用

class string { public: string(const char *str=NULL); string(const string& str);     //copy构造函数的参数为什么是引用呢? string& operator=(const string & str); //赋值函数为什么返回值是引用呢?参数为什么是引用呢? ~string(); }; 下面我就给大家解释一下: class String1 { public: String1(const char*

一起学Java(二十六)----- 对象之间赋值

不积跬步,无以至千里:不积小流,无以成江海. Java语言基础 Java对象之间赋值 赋值是用等号运算符“ = ”进行的,在对对象进行“赋值”时,实际就是将句柄从一个地方复制到另一个地方.这意味着假若为对象使用“A = B”,那么A和B最终都会指向最初只有B才指向的那个对象.也就是说这个时候他们两个引用了同一块内存地址. class Number{ int i; } public class Test { public static void main(String[] args) { Numb

JS 内存堆栈原理(注销引用对象后带来的问题)

var a = { name: 123}; var b = a; a.name; 123 b.name; 123 a.name = 'wolf'; "wolf" b.name "wolf" a.name = null; //注销此引用对象的内存,引用此引用对象的对象,失去对引用对象的引用,获得属于自己的引用对象副本; null b.name null a = null; null b Object {name: null}

设计一个不强引用对象的单例字典

大家都知道,使用NSDictionary存储对象的时候会强引用对象,导致被存储对象的引用计数+1,有时候,我们想用单例来存储对象,但又不希望强引用存储的对象,这该怎么实现呢? 在这里,我们可以使用NSMapTable来实现这个功能. 我直接给出源码: WeakDictionary.h   +   WeakDictionary.m // // WeakDictionary.h // 弱引用字典 // // http://www.cnblogs.com/YouXianMing/ // Copyrig

Andorid Binder进程间通信---Binder本地对象,实体对象,引用对象,代理对象的引用计数

本文参考<Android系统源代码情景分析>,作者罗升阳. 一.Binder库(libbinder)代码: ~/Android/frameworks/base/libs/binder ----BpBinder.cpp ----Parcel.cpp ----ProcessState.cpp ----Binder.cpp ----IInterface.cpp ----IPCThreadState.cpp ----IServiceManager.cpp ----Static.cpp ~/Androi