细数javascript简单被忽略的语法陷阱

细数javascript容易被忽略的语法陷阱JavaScript 可算是世界上最流行的编程语言,它曾被 Web 开发设计师贴上

细数javascript容易被忽略的语法陷阱

JavaScript 可算是世界上最流行的编程语言,它曾被 Web 开发设计师贴上噩梦的标签,虽然真正的噩梦其实是 DOM API,这个被大量的开发与设计师随手拈来增强他们的 Web 前端的脚本语言,如今越来越被重视,虽则如此,JavaScript 仍然拥有很多让人费解的东西。

?1. 它以 Java 命名,但并不是 Java

它最初叫 Mocha, 接着改名为 LiveScript,最后才确定命名为 JavaScript,根据历史记录,Java 的命名与 Netscape 和 Sun 之间的合作有关,作为交换条件,Netscape 在他们备受欢迎的浏览器中创建了 Java 运行时。值得一提的是,这个名字的出台几近一个玩笑,要知道,LiveScript 和 Java 在客户端脚本方面存在敌对关系。

不管怎么说,人们后来不得不一再澄清的一件事就是,JavaScript 和 Java 毫无关系。

2. Null 是个对象?

看看这段代码,它返回的是 object。

?

Js代码
  • console.log(typeof?null);?//?object????

    ??

    这实在令人费解,假如 null 表示空值,它怎么可以是对象?简单说,它是 JavaScript 最初版本的错误,这个错误甚至被微软的 JScript 直接借用。

    3. NaN !== NaN

    NaN,表示一个非数字的值,然而问题是,NaN不等于任何东西,甚至不等于它自己。

    ?

    Js代码
  • console.log(NaN?===?NaN);?//?false????

    ??

    这显然不对,事实上,如果要判断一个值确实是 NaN,你需要用 isNaN() 函数。

    4. 全局变量

    对全局变量的依赖一直被视为 JavaScript 最坏的部分(ECMA 的 JavaScript 5 已经去掉了全局变量,请参阅Js代码

  • console.log(navigator.userAgent);?????
  • //?Mozilla/5.0?(Macintosh;?U;?Intel?Mac?OS?X?10_5_8;?en-us)?AppleWebKit/531.21.8?(KHTML,?like?Gecko)?Version/4.0.4?Safari/531.21.10????

    ?

    是否注意到其中的第一个单词Js代码

  • Mosaic/0.9?????//?browser?name?/?version?number???

    ??

    这很合理,因此当 Netscape 出来的时候,它保留了 Mosaic 这个传统,还在后面添加了一个加密方式部分。

    ?

    Js代码
  • Mozilla/2.02?[en]?(Win95;?I)?????//?browser?name?/?version?/?encryption???

    ?

    到目前为止,一切安好,直到 IE3 发布,当 IE3 发布的时候,Netscape 正如日中天,那时,很多服务器和程序已经部署了客户端探测机制,以便认出 Netscape,虽然现在看来,这很值得争议,但当时并没什么。当 IE 初次推出它们的 User Agent 标志的时候,是这个样子:

    ?

    ?

    Js代码
  • MSIE/3.0?(Win95;?U)????

    ?

    这让 IE 很被动,因为 Netscape 已经能被很多服务器识别,因此,开发者们干脆希望 IE 被误认为 Mozilla,然后,再单独加一个 IE 的标签。

    ?

    Js代码
  • Mozilla/2.0?(compatible;?MSIE?3.0;?Windows?95)????

    ??

    如今,几乎所有浏览器都步 IE 后尘,将自己标识为 Mozilla,这大概是一种连锁反应。

    6. 不一致的函数范围

    参看以下代码:?

    ?

    Js代码
  • function?that?will?call?a?function?with?the?name?equal?to?parameter?fn.?????
  • function?foo(fn)?{?????
  • ????if?(typeof?fn?===?"function")?{?????
  • ????????fn();?????
  • ????}?????
  • }?????
  • ???
  • //?Create?an?object?with?a?property?and?a?method.?????
  • var?bar?=?{?????
  • ????barbar?:?"Hello,?World!",?????
  • ????method??:?function()?{?????
  • ????????alert(this.barbar);?????
  • ????}?????
  • };?????
  • ????
  • bar.method();?//?Alerts?Hello,?World!?????
  • foo(bar.method);?//?If?we?call?the?foo?function?add?pass?the?"bar.method"?method,?it?somehow?alerts?"undefined."?????
  • foo(function()?{?bar.method();?});?//?alerts?Hello,?World,?after????

    ?

    foo(bar.method) 返回结果不同原因是,method 函数是被当作 windows 对象,而不是 bar 下的对象调用的。要解决这个问题,我们必须从传递的匿名函数中调用 bar.method() 。

    7. 位操作符

    JavaScript 和 Java 有不少共同之处,如位操作。

    • &细数javascript简单被忽略的语法陷阱?Js代码
    • console.log(.2?+?.4);?//?0.6000000000000001?????

      为什么会这样?简单说,因为 JavaScript 使用 IEEE 标准进行二进制浮点运算,不过,对整数计算是没问题的。

      10. 莫名其妙的代码错误

      看看以下两段代码:

      ?

      Js代码
    • //?braces?on?the?right?????
    • return?{?????
    • ?foo?:?bar?????
    • };?????
    • ????
    • //?braces?on?their?own?line?????
    • return????
    • {?????
    • ??foo?:?bar?????
    • };????

      ??

      它们应该是一样的,只是 { 位置不同而已,是吧。然而我们再看下面的代码:

      ?

      Js代码
    • var?foo?=?function()?{?????
    • ??????return?{?????
    • ????????a?:?'b'????
    • ????};?????
    • ????
    • }();?????
    • ????
    • alert(foo.a);?//?b?????

      ?

      如果我们把其中的

      ?

      Java代码
    • return??{?????
    • ????a?:?'b'????
    • };????

      ???

      换成

      ?

      1. return????
      2. {?????
      3. ????a?:?'b'????
      4. };?????

      ?

      就会引发错误,这是因为 JavaScript 有一个功能,会纠正它认为错误的代码书写,它会自作聪明地在 return 这个词后面插入一个 ";" ,错误因此而生。

      ?

      Js代码
    • return;?//?JS?incorrectly?adds?this?semicolon.?????
    • {?????
    • ????a?:?'b';?//?It'll?add?a?semicolon?here?as?well,?because?it?doesn't?realize?that?this?is?an?object.?????
    • };????

      ?附:

      1、

      ?

                  IEEE。

                  既然提到了IEEE,那再来一个。

                  0.9999999999999999

                  ?

                  6、

                      0.1?+?0.1?+?0.1?+?0.1?+?0.1?+?0.1?+?0.1?+?0.1?+?0.1?+?0.1??
                    1 楼 kuchaguangjie 2010-06-12   这都没啥吧 ~~~

                    这都不是什么事 ~~~ 2 楼 chemzqm 2010-06-13   都是些极少会遇到的问题,大可不必放在心上 3 楼 zhameng 2010-06-14   没事还是看一下,NaN!=NaN 的情况我就遇到过。 4 楼 zhengtianbing123 2010-06-22   parseInt('08') -> 0
                    这个我的确遇到过,