这几天跟几个同事聊天发现他们对javascript什么时候该用new都不是很了解。

1、javascript的function什么时候该new什么时候不该new?
我觉得主要的问题还是集中在javascript的弱类型上面。

new在干什么

首先我们知道new是干什么,以我们java或.net的语言经验显然在创造对象。是的,不管是java还是.net。他是在创建一个对象。

new后面是什么

那么我们考虑一下new的后面是什么,(java和.net)一般是被一个class修饰的类名称。那么我们考虑一下,我们实例一个对象是干什么或者说设计者的目的是什么,那么一般情况下对象都会包含这些成员,属性与行为或者其中之一(我们在javaEE中DAO只有行为,POJO只有属性),有没有看到过既没有属性也没有行为的对象(当然类可以这么设计,但是没有意义)。

javascript的new干了什么
那么javascript的new干了什么?new其实开辟了内存空间创建了一个object这个object就是this,然后这个this的prototype指向了函数本身的prototype。
也就是说去new一个function的时候,开辟了一个this,这个this就是对象本身,再想想你去实例一个对象。你要拿到对象的成员,属性或方法或其中之一。this本身有几种方式能声明成员,一种在function函数体内部用this.的方式声明,例如:this.a = '123',其实就是给他的a属性赋了一个‘123’字符串,当然也可以赋值行为。还有种方式就是通过原型继承,通过function函数的.prototype的方式。
好了,因为javascript是弱类型,他没有class修饰,没有是否有返回值修饰,只有一个function修饰。所以function是否是构造函数很难通过函数头知道。所以是否需要去new就需要你去揣摩function的目的,他到底是不是构造函数。

实例代码说明
既然他是弱类型,他们可以根据内部的条件选择到底是做构造函数用,还是做普通函数用。再加上我们很多程序员都是其他语言出身,很少有人系统的学习了javascript,所以就很混淆。
下面我们来看混淆的例子吧。

Js代码

  • function Hello() {
  • this.a = '123';
  • this.b = function () {
  • alert('b');
  • }
  • return this;
  • }
  • Hello.prototype.c = function() {
  • alert('c');
  • }
  • var aHello = new Hello();
  • var bHello = Hello();
  • alert(aHello.a)
  • alert(bHello.a)
  • aHello.b();
  • bHello.b();
  • aHello.c();
  • bHello.c();

你会发现bHello.c()是执行不了的。在看看上面的函数,他为什么既能new又能不new。
new其实开辟了内存空间创建了一个object这个object就是this,然后这个this的prototype指向了函数本身的prototype。
不new就是执行了这个函数,最后return this就是返回了这个执行函数的宿主,其实就是window本身。
所以c函数是绑定在Hello的prototype上的,所以window上根本没有。

但是就出现了一个问题,就是如果在不执行c方法或者c本身不是通过原型继承的方式的话(就是不通过Hello的prototype方式,通过直接给this赋值的方式),其实创建的this的内容和window增加的内容是一样的,程序员会本能的以为new和不new是一样的。这样就掉坑里去了。

总结:javascript弱类型语言,一个函数即使是普通的执行函数,你new或不new都会出现编译器异常。
new与不new我们要做好以下几点。
1、首先大家要了解new本身干了什么,然后看函数创建者的意图,看函数结构。
2、一个好的程序员在提供某个javascript工具类或公用方法时,应该注释告诉你的调用者怎么去使用你提供的公用内容,或者提供工厂方法。

JS基础如何理解对象的更多相关文章

  1. JS的从理解对象到创建对象

    JavaScript不是一门真正的面向对象语言,因为它连最基本的类的概念都没有,因此它的对象和基于类的语言中的对象也会有所不同.ECMA-262把对象定义为:“无序属性的集合,其属性可以包含基本值.对 ...

  2. JS面向对象设计-理解对象

    不同于其他面向对象语言(OO,Object-Oriented),JS的ECMAScript没有类的概念, 它把对象定义为"无序属性(基本值.对象.函数)的集合",类似于散列表. 每 ...

  3. 【2017-03-28】JS基础、windows对象、history对象、location对象

    一.JS基础 JS - javaScript 1.js功能: 1).进行数据的运算.2).控制浏览器的一些功能.3).控制元素(属性.内容.样式) js引用位置: 可以放在html页的任意位置. 推荐 ...

  4. Js基础之常用对象

    今天来总结一下js中的常用对象: 1.string对象 常用方法: charAt():返回在指定位置的字符. charCodeAt():返回在指定的位置的字符的 Unicode 编码. concat( ...

  5. JS基础-内置对象【字符串+Date+Math】

    JS内置对象[字符串] // charAt() 返回字符 // charCodeAt() 返回字符的unicode编码 var str="hello world"; console ...

  6. JS基础常识理解

    <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/ ...

  7. JS基础之BOM对象

    BOM 对象 JavaScript分为 ECMAScript,DOM,BOM. BOM(浏览器对象模型),可以对浏览器窗口进行访问和操作.使用 BOM,开发者可以移动窗口.改变状态栏中的文本以及执行其 ...

  8. JS基础语法---Array对象的方法

    Array对象的方法   Array.isArray(对象)---->判断这个对象是不是数组 instanceof关键字 判断对象是不是数组类型:两种方法: //1 instanceof var ...

  9. JS基础语法---String对象下的方法(字符串的方法)

    实例方法---->必须要通过new的方式创建的对象(实例对象)来调用的方法 静态方法---->直接通过大写的构造函数的名字调用的方法(直接通过大写的对象名字调用的) 字符串的常用属性: . ...

随机推荐

  1. MapXtreme在asp.net中的使用之加载地图(转)

    MapXtreme在asp.net中的使用之加载地图(转) Posted on 2010-05-04 19:44 Happy Coding 阅读(669) 评论(0) 编辑 收藏 1.地图保存在本地的 ...

  2. FreeImage裁剪示例

    //截图 int cropImage(const char* file, int left, int top, int right, int bottom, BYTE* &dstData, D ...

  3. myEclipse + phonegap-2.9.0 总跳出3个脚本提示

    环境:myEclipse + phonegap-2.9.0按照教程全部完毕后,浏览页面时,总会跳出3个脚本提示:1:gap:["Device","getDeviceInf ...

  4. php 变量

    unset() 卸载 静态变量static $i=2; 1.是在所有对函数调用中共享; 2.只有在第一次调用的时候赋值 <?php /* * 一.任何数量的参数 * func_get-args( ...

  5. Windows Message Queue--hdu1509

    Windows Message Queue Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/32768 K (Java/Ot ...

  6. UVA 1839 Alignment

    还是最长上升子序列... 本题是求队列中任一士兵都能从左边或者右边看到队伍外: 即某一士兵左边为上升子序列,右边为下降子序列.求两个序列和,再用总数减去: #include <iostream& ...

  7. ZigBee 协议规范

      ZigBee协议栈体系结构由应用层.应用汇聚层. 网络层.数据链路层和物理层组成,如下图所示:   图1 ZigBee 协议栈体系的层次结构      应用层定义了各种类型的应用业务,是协议栈的最 ...

  8. CC++初学者编程教程(15) 基于cocos2dx的安卓打包环境

    1首先安装python 2 单击next 3 选择默认路径,单击next 4选择完全安装,单击next 5单击next开始安装 6 安装完成 7 设置环境变量 8 添加python的路径到path 9 ...

  9. VC实现图片拖拽及动画

    基础知识 1.PictureBox控件的使用 2.加载位图文件 1.通过文件路径获得位图句柄 //获得位图句柄  void CMovePictureDlg::GetHandleFromPath(CSt ...

  10. DB操作用法总结。

    用到了慢慢总结.用到了随时更新. 其实可以看手册了.但是看了完了手册之后,还是记不住. 1. mysql select * from table where id in(1,2,3,3,4) 怎么能显 ...