js中对象引用出现的问题
先看一个特别不符合直觉的代码
<script type="text/javascript">
var a = [1,2,3,4];
var b = [1,2,3,4];
console.log(a==b); //出现false,按照常规理解,a和b应该是一样的,都是[1,2,3,4],同时也说明,js中不能这么判断数组时候相同
</script>
再看代码
<script type="text/javascript">
var a = 3;
var b = 3;
console.log(a==b); //true
</script>
第二段代码为true很好理解,都是3,那第一段代码为何为false,都是[1,2,3,4]呀
----------
在js中,基本类型的变量(有数字,字符串,布尔值)赋值的时候,就是值复制过去,以后相互之间就没有关系了。
比如说:
<script type="text/javascript">
var a = 5;
var b = a; //a是基本类型数据,赋值给b,那么在内存中,b就存了a的值5,以后各走各的路,a,b没有关系了。
b += 5;
console.log(a,b); // 5,10
</script>
<script type="text/javascript">
var a = [1,2,3,4];
var b = a;
var c = [1,2,3,4];
console.log(a==b); //true;
console.log(a==c); //false; //b是a赋值过去的,现在更改b的内容,再看看a
b.push(5);
console.log(a); // [1, 2, 3, 4, 5 ] 很奇怪吧,a也变了啊,这里对a没有操作呀???
</script>
上面的代码,a不是基本类型,是个数组对象,赋给b的时候,改动b也改动了a,真是奇怪。这就是在js中,当a不是基本类型数据时,内存中a存的是一个内存地址,a赋值给b时候,ab共同指向一个内存地址,改动了a,也就改动了b,改动了b,也就改动了a,如下
<script type="text/javascript">
var a = [1,2,3,4];
var b = a;
var c = [1,2,3,4];
console.log(a==b); //true;
console.log(a==c); //false; //b是a赋值过去的,现在更改b的内容,再看看a
b.push(5);
a.push(6);
console.log(a); // [1, 2, 3, 4, 5 ,6 ] 很奇怪吧,a也变了啊,这里对a没有操作呀???
console.log(b); // [1, 2, 3, 4, 5 ,6 ]
console.log(a==b); //true;
</script>
再看一段代码
<script type="text/javascript">
var a = [1,2,3,4];
var b = a; //b是a赋值过去的,现在更改b的内容,再看看a
b = [1,2,3,4,5]; //这里不用b.push(5);看看什么变化
console.log(a); // [1, 2, 3, 4 ] a不变
console.log(b); // [1, 2, 3, 4, 5 ]
console.log(a==b); //false;
</script>
是不是很困惑,不是说了改动b,a也跟着动吗?
第6行代码,不是b对象改动,而是又重新赋值一个对象给了b,b是数组对象的另一个对象实例(只要程序中出现赋值,那就是重新生成),他俩也就没关系了,如果用b的某个方法,改动的b的值,那a和b仍然指向同一个地址!
---------------------------
所有的一切,总结出来一句话:
在js中,基本类型数据,在内存中存的就是个数据
a | 5
b | 5
a,b值相同,就是a==b
但是对象不一样
在内存中,对象存的是个地址,a和b这两个对象相同的话,需要值和地址都相同才可以。
a | 内存指针1
b | 内存指针1
这样ab才相同。
--------------------------
在面向对象程序中,如果用这种方式创建对象,如下
<script type="text/javascript">
function CreatePerson(name){
this.name = name;
this.test = function(){
console.log(this.name);
}
} var my_obj1 = new CreatePerson('张三');
var my_obj2 = new CreatePerson('李四'); alert(my_obj1.test == my_obj2.test); //false //虽然代码上是一样的,但是my_obj1和my_obj2是两个对象实例,他们各自在内存中开辟一个地方,放置test方法,如果对象实例很多,就比较占内存了。 </script>
所以,要更改下,用prototype,在对象中,不同的地方,如属性,写在构造函数里,相同的地方,如方法,用原型来写。如下:
<script type="text/javascript">
function CreatePerson(name){
this.name = name;
} CreatePerson.prototype.test = function(){
console.log(this.name);
} var my_obj1 = new CreatePerson('张三');
var my_obj2 = new CreatePerson('李四'); alert(my_obj1.test == my_obj2.test); //true
my_obj1.test(); // 张三
my_obj2.test(); // 李四 </script>
js中对象引用出现的问题的更多相关文章
- 别再为了this发愁了------JS中的this机制
别再为了this发愁了------JS中的this机制 题记:JavaScript中有很多令人困惑的地方,或者叫做机制.但是,就是这些东西让JavaScript显得那么美好而与众不同.比方说函数也是对 ...
- JS中的this用法详解
随着对js的深入学习和使用,你会发现它里面包含了很多令人困惑的机制,比如对象.闭包.原型链继承等等,而这其中肯定包含令你现在或者曾经费解的this,如果你不把心一横,花点时间还真不明白这个this的用 ...
- js中的数据类型及其转换
Js中的数据类型 Js中的数据类型一共有六种,即number,string,boolean,underfine,null,object. 一,number Number数据类型指的是数字,可以为整型, ...
- Javascript基础 - js中曾经忽略的知识点
深入那些曾经忽略的Javascript知识 1. parseInt(string, [radix]),parseFloat(string) 一般我们省略第二个参数,parseInt(‘100’) == ...
- JS中如何进行对象的深拷贝
在JS中,一般的=号传递的都是对象/数组的引用,并没有真正地拷贝一个对象,那如何进行对象的深度拷贝呢?如果你对此也有疑问,这篇文章或许能够帮助到你 一.对象引用.浅层拷贝与深层拷贝的区别 js的对象引 ...
- JS中让新手倍感震惊、违反直觉、出乎意料、的一些知识点汇总记录
本文记录在自己学习js过程中,违反直觉,出乎意料,倍感震惊的知识点.当然,不了解这个知识点,很容易出错,因为毕竟违反直觉,出乎意料,倍感震惊嘛! 1. 两个内容一样的数组竟然不相等? var a = ...
- JS中的六大数据类型
js中有六种数据类型,包括五种基本数据类型(Number,String,Boolean,Undefined,Null),和一种复杂数据类型(Object). typeof 操作符 由于js中的变量是松 ...
- JS中变量的存储
JS中的变量是保存在栈内存中的 基本数据类型的值直接在栈内存中存储: 值与值之间是独立存在的,修改一个变量不会影响其他变量: var a=20; var b=a; a++; 对象(引用数据类型)是保存 ...
- 别再为了this发愁了:JS中的this机制
题记:JavaScript中有很多令人困惑的地方,或者叫做机制.但是,就是这些东西让JavaScript显得那么美好而与众不同.比方说函数也是对象.闭包.原型链继承等等,而这其中就包括颇让人费解的th ...
随机推荐
- 老毛桃pe安装系统
1.准备一个空白U盘,插入电脑. 2.下载老毛桃pe 3.下载完成后,打开老毛桃,默认制作成系统盘,傻瓜操作,无需修改参数 4.打开浏览器,下载要安装的系统 www.msdn.itellyou.cn ...
- .NetCore 使用Cookie
1.首先我们在Startup下面的ConfigureServices中注册授权认证服务以及AddCookie services.AddAuthentication(CookieAuthenticati ...
- .NET Core微服务之基于EasyNetQ使用RabbitMQ消息队列
Tip: 此篇已加入.NET Core微服务基础系列文章索引 一.消息队列与RabbitMQ 1.1 消息队列 “消息”是在两台计算机间传送的数据单位.消息可以非常简单,例如只包含文本字符串:也可以更 ...
- .NET Core微服务之开源项目CAP的初步使用
Tip: 此篇已加入.NET Core微服务基础系列文章索引 一.CAP简介 下面的文字来自CAP的Wiki文档:https://github.com/dotnetcore/CAP/wiki CAP ...
- QLineEdit拾遗:数据的过滤、验证和补全
QLineEdit是使用频率最高的控件之一,当我们想获取用户输入时自然而然得会用到它. 通常我们会将QLineEdit的信号或其他控件的信号绑定至槽函数,然后获取并处理编辑器内的数据.你会觉得我们拿到 ...
- 用jQuery做一个选项卡
1.首先我们点击选项卡的标题栏来改变内容
- 【Tomcat】Tomcat工作原理及简单模拟实现
Tomcat应该都不陌生,我们经常会把写好的代码打包放在Tomcat里并启动,然后在浏览器里就能愉快的调用我们写的代码来实现相应的功能了,那么Tomcat是如何工作的? 一.Tomcat工作原理 我们 ...
- 使用 DotNet CLI 创建自定义的 WPF 项目模板
描述 当我们安装完 DotNetCore 3.0 版本的 SDK 后,我们就可以创建基于 DotNetCore 的 WPF 项目模板,通过如下 CLI 可以方便快捷的创建并运行我们的项目: dotne ...
- Android为TV端助力 使用shared注意事项
不要存放大的key和value!我就不重复三遍了,会引起界面卡.频繁GC.占用内存等等,好自为之! 毫不相关的配置项就不要丢在一起了!文件越大读取越慢,不知不觉就被猪队友给坑了:蓝后,放进defalu ...
- JMeter写入文件
之前我们推文讨论过如何使用jmeter读取文件, 比如csv, txt文件读取, 只要配置csv数据文件, 即可非常容易的从文件中读取想要的数据, 但是如果数据已经从API或者DB中获取, 想存放到 ...