JavaScript学习笔记1:JavaScript学前介绍与基本概念

主要根据图书《JavaScript高级程序设计(第3版)》

1、JavaScript是一种专门与网页交互而设计的脚本语言,由 下列三个不同的部分组成:
1)ECMAScript,由ECMA-262定义,提供核心语言功能;
2)文档对象模型(DOM) ,提供访问和操作网页内容的方法和接口;
3)浏览器对象模型(BOM),提供与浏览器交互的方法和接口。

现状:
JavaScript 的这三个组成部分,在当前5个主要浏览器(IE, Firefox, Chrome, Safari 和Opera)中都得到了不同程度的支持。其中,所有浏览器对 ECMAScript 第 3 版的支持大体上都还不错,而对ECMAScript 5 的支持程度越来越高,但对DOM的支持则彼此相差比较多。对已经纳入 HTML5 标准的 BOM 来说,尽管各浏览器都实现了某些众所周知的共同特性,但其他特性还是会因浏览器而异。


2、在HTML中使用JavaScript
1)在HTML页面中执行JS的3中方法
嵌入执行(2种方法):
<body>
<a href="javascript:alert('运行JavaScript!');">运行 JavaScript</a>
<script type="text/javascript">
    alert("直接运行的JavaScript!");
</script>
</body>

导入外部js文件:
<script src="test.js" type="text/javascript"></script>
这个时候标签内就不要再嵌入JS代码, 导入外部JS的时候,嵌入的代码会被忽略

3、需要注意的
把JavaScript插入到HTML页面中要使用<script>元素。使用这个元素可以把JavaScript嵌入到页面中,也可以包含外部JS文件。
1)包含外部JavaScript文件时,必须将src属性设置为指向响应文件的URL。而这个文件可以是与它的页面位于同一服务器的文件,也可以是其他任何域中的文件。
2)所有<script>元素都会按照它们在页面中出现的先后顺序依次被解析。在不适用 defer 和async 属性的情况下,只有在解析完前面<script>元素中的代码之后,才会开始解析后面<script>元素中的代码。
3)由于浏览器会先解析完不适用defer 属性的<script>元素中的代码,然后再解析后面的内容,所以一般应该吧<script>元素放在页面最后,即主要内容后面,</body>标签前面。
4)使用  defer 属性可以让脚本在文档完全呈现后再执行。延迟脚本总是按照指定它们的顺序执行。
5)使用  async 属性可以表示当前脚本不必等待其他脚本,也不必阻塞文档呈现。不能保证异步脚本按照它们在页面中出现的顺序执行。
另外, 使用<noscript>元素可以指定在不支持脚本的浏览器中显示的替代内容。但在启用了脚本的情况下,浏览器不会显示<noscript>元素中的任何内容。

4、<script>元素  HTML4.01为<script>定义了6个属性,全是可选,language已废弃
1)type :考虑到约定俗成和最大限度的浏览器兼容性,还是text/javascript  。其实标准来说有好几个其他值
2)src :表示包含要执行代码的外部文件
3)charset:表示通过src属性指定的代码的字符集。由于大多数浏览器会忽略它的值。
4)language:已废弃,原来用于标识编写代码使用的脚本语言(如JavaScript、JavaScript1.2、VBScript)
5)defer:表示脚本可以延迟到文档完全被解析和显示之后再执行,只对外部脚本文件有效。
6)async:可选,表示应该立即下载脚本,但不应妨碍页面中的其他操作,如下载其他资源或等待加载脚本。支队外部脚本有效。

注意1
在<script>嵌入JS代码是,不要在代码中的任何地方出现"</script>"字符串,浏览器加载时会产生错误,会认为那是结束的</script>标签,如下文:
<script type="text/javascript">
    function sayScript(){
         alert("</script>");
    }
</script>

但是通过转义字符"\"可以解决这个问题
<script type="text/javascript">
    function sayScript(){
         alert("<\/script>");
    }
</script>

注意2
XHMTL可以容忍省略</script>,但HTML文档不行。

5、 XHTML代码的规则 比HTML严格得多,如
1)<  和>  直接a < b 会报错,要改写成实体编码&lt; 还可以
2)用 <![CDATA[...这里是不需要的任意格式的文本内容...]]>  语法包裹内容  。有时候还配合注释使用
//<![CDATA[
...这里是不需要的任意格式的文本内容...
//]]>  
3)在XHTML格式中,要把defer属性设置为 defer="defer" ,async也一样

6、<noscript>元素
当浏览器不支持JavaScript时,如何让页面平稳退化。

<!DOCTYPE html>
<html>
<head>
 <title>ceshi</title>
</head>
<body>
 <noscript>
  <p>本页面需要浏览器支持(启用)Javascript</p>
 </noscript>
</body>
</html>

不推荐使用的(为了让不支持 <script> 标签的浏览器能隐藏嵌入的JavaScript代码:
 <script><!--
  alert("Hi");
 //--></script>

Chrome测试代码:
<!DOCTYPE html>
<html>
<head>
 <title>ceshi</title>
</head>
<body>
 <noscript>
  <p>本页面需要浏览器支持(启用)Javascript</p>
 </noscript>
 <script><!--
  alert("Hi");
 //--></script>
</body>
</html>

正常时:

JavaScript学习笔记1:JavaScript学前介绍与基本概念

禁用当前页面JS后:

JavaScript学习笔记1:JavaScript学前介绍与基本概念

JavaScript学习笔记1:JavaScript学前介绍与基本概念

7、文档模式
从IE5.5开始,引入了“文档模式”的概念,这个概念是通过使用文档类型(doctype)切换来实现的,后来其他浏览器也纷纷效仿。
最初的两周文档模式是:混杂模式、标准模式。混杂模式让IE的行为与(包含非标准特性的)IE5相同,而标准模式则让IE的行为更接近标准行为。
这两种模式主要影响CSS的呈现,也会影响JS的解释执行。现阶段,开发前端代码,声明文档模式,让浏览器以适当的模式去解析,是有必要的。
详情参见:
<!DOCTYPE> 声明
Web 世界中存在许多不同的文档。只有了解文档的类型,浏览器才能正确地显示文档。
HTML 也有多个不同的版本,只有完全明白页面中使用的确切 HTML 版本,浏览器才能完全正确地显示出 HTML 页面。这就是 <!DOCTYPE> 的用处。

<!DOCTYPE> 不是 HTML 标签。它为浏览器提供一项信息(声明),即 HTML 是用什么版本编写的。


JavaScript基本概念


JavaScript语言的 核心特性在ECMA-262中是以名为 ECMAScript 伪语言的形式来定义的。
ECMAScript 包含了所有基本的语法、操作符、数据类型以及完成基本的计算任务所必需的对象,但是 没有对取得输入和产生输出的机制作出规定。理解ECMAScript  及其纷繁复杂的各种细节,是理解其在Web浏览器中的实现---JavaScript的关键。目前大多数实现所遵循的都是 ECMA-262 第3版,但很多都已经开始着手实现第5版了。以下简要总结了ECMAScript中基本的要素。
1)ECMAScript  的 基本数据类型包括  Undefined、Null、Boolean、Number和String
2)与其他语言不同,ECMAScript   没有为整数和浮点数值分别定义不同的数据类型, Number类型可用于表示所有数值
3)ECMAScript  也有一种 复杂的数据类型,即 Object类型,该类型是这门语言中所有对象的基础类型。
4) 严格模式为这门语言中容易出错的地方施加了限制。
5)ECMAScript  提供了很多与C 及其他类C语言中相同的基 本操作符,包括算数操作符、布尔操作符、关系操作符、相等操作符及赋值操作等。
6)ECMAScript  从其他语言借鉴了很多 流控制语句,例如if、for、switch  ,还 又一些和其他语言很不同的,比如 for in
7) 无须指定函数的返回值,因为ECMAScript  函数都可以在任何时候返回任何值。
8)实际上, 未指定返回值的的函数返回的是一个特殊的 undefined 值。
9)ECMAScript  也没有函数签名的概念,因为其函数参数是以一个包含零或者多个值的数组的形式传递的。
10) 可以向ECMAScript    函数传递任意数量的参数,并且可以通过arguments 对象来访问这些参数
11)由于不存在函数签名的特性, ECMAScript    函数不能重载

1、语法
1) 区分大小写
ECMAScript 中的 一切(变量、函数名和操作符)都区分大小写。PHP是变量区分,函数名不区分。
2)标识符:第一个字符必须是字母、下划线_或美元符号$,其他字符也可以是数字
标识符中的字母也可以包含扩展的ASCII或Unicode字符,但是不推荐。
按照惯例,标识符采取驼峰大小写格式,也就是第一个字母小写,剩下每个单词首字母大写,如firstSecond、myCar、doSomethingImportant。
3)注释
//    /*  */
多行注释推荐如下:
/*
*
*
*/
4)严格模式
ECMAScript 5引入了严格模式概念(strict mode),严格模式为JS定义了一种不同的解析与执行模型。
要在整个脚本中启用严格模式,可以在顶部添加如下代码:
"use strict"
这其实是一个编译指示,告诉支持的JavaScript引擎切换到严格模式。
函数内部的上方包含这条提示,也可以指定函数在严格模式下执行;
function doSomething(){
    "use strict"
    //函数体
}
5)语句, 分号; 结尾,如果省略,由解析器确定语句结尾。推荐代码块用{}包含,及时只有一条语句。
6)定义变脸,用var
如果在 函数体内定义变量时,省略var,会创建一个全局变量

2、数据类型
1)typeof 操作符,对一个值使用typeof 操作符肯恩返回下列某个字符串,:
“undefined”-- 如果这个值未定义
“boolean”-- 如果这个值是布尔值:true false
“string”-- 如果这个值是字符串
“number”-- 如果这个值是数值
“object”-- 如果这个值是对象或者null
“function”-- 如果这个值是函数。
注:函数在ECMAScript 中是对象,然后,函数确实有一些特殊的属性,因此通过typeof 操作符来区分函数和其他对象时有必要的。
Undefined 类型只有一个值:undefined,Null类型也只有一个值,是null  。从逻辑角度看,null值表示一个空对象指针,如果用typeof 检测null会返回"object"。实际上,undefined是派生于null的。
2)
于JS保存熟知的方式,可以保存正零(+0)和负零(-0);
在进行数值计算时,所有以八进制(0)和十六进制(0x)表示的数值最终豆浆杯转换成十进制数值。
保存浮点数的内存空间是证书的两倍,ECMAScript 会不失时机将浮点数转换成整数值。
舍入误差。
NaN,即费数值(Not a Number)是一个特殊的数值,表示本来要返回数值的操作数未返回数值的情况。(NaN与任何值都不想等,包括NaN本身。isNAN()函数接受一个参数,确定是否不是数值或者不能转换为数值)
数制转换函数:将非数值转换为数值
Number()  parseInt() parseFloat()  有区别

3)字符串
与PHP中双引号和单引号会影响对字符串的解释方式不同,EMCAScript中,这两种无什么区别。
\ xnn :以十六进制代码nn表示的一个字符(其中n为0~F)。例如\x41 表示“A”。
\ xnnnn :以十六进制代码nnnn表示的一个Unicode字符。
JS中字符串是不可变的,字符串一旦创建,要改变某个变量存的字符串,就先销毁原来的字符串,然后再用另一个包含新值的字符串填充该变量。
转换成字符串:toString()方法,几乎每个值都有,然后要把某个值转换为字符串,可以用加号操作符把它与一个字符串("")加在一起。

4)object类型,ECMAScript中的对象其实就是一组数据和功能的集合。
从技术角度讲ECMA-262中对象的行为并不一定适用于JS中的其他对象。因为浏览器环境中的对象,比如BOM和DOM中的对象,都属于宿主对象,因为它们是有宿主实现提供和定义的。因为宿主对象可能会也可能不会集成Object。

3、操作符
1)
一元操作符、
位操作符(位操作符用于最基本的层次上,ECMAScript中所有数值都以IEEE-754 64位格式存储,但是位操作符不是直接操作64位的值,而是先将64位的值转换成32位的整数,然后执行操作,最后再将结果转换回64位)、
布尔操作符(逻辑)、
乘性操作符、
加性操作符、
关系操作符(<=  >=)、
相等操作符(==、===、!= 、!==)、
条件操作符、
复制操作符、
逗号操作符(,):可以在一条语句中执行多个操作,复制时总返回表达式最后一项

4、语句
1)if else、do-while、while、for 和C语言中都相似
2) for-in语句(这个和python中个for有些相似):
for-in是一种精准的迭代语句,可以用来枚举对象的属性
 for (property in expression) statement
示例:
<!DOCTYPE html>
<html>
<head>
    <title>For-In Statement Example 1</title>
</head>
<body>
    <script type="text/javascript">
        for (var propName in window) {
             document.write(propName);
             document.write("<br />");
        }
    </script>
</body>
</html>
注意:ECMAScript 对象的属性没有顺序。因此,通过for-in 循环输出的顺序是不可预测的,可能会因浏览器而异。但是如果表示要迭代的对象的变量值是null或undefined ,for-in语句会抛出错误,ECMAScript 5更正了这一行为,改成只是不执行循环体。因此,有必要使用for-in之前,先确认该 对象的值是不是null或者undefined。
Safari3 以前版本的for-in语句有一个bug,会导致某些属性被返回2次。
3) label语句:添加标签,一边将来使用,可由break或continue语句引用。加标签的语句一般与for语句等循环语句配合使用。

例子:
<!DOCTYPE html>
<html>
<head>
    <title>Break Statement Example 2</title>
    <script type="text/javascript">
        var num = 0;
       
         outermost:
        for (var i=0; i < 10; i++) {
             for (var j=0; j < 10; j++) {
                if (i == 5 && j == 5) {
                     break outermost;
                }
                num++;
            }
        }
       
        alert(num);     //55
    </script>
</head>
<body>
</body>
</html>
学过C的可能有些不理解,事实上这样写语法能正确执行。
4)with语句
将代码的左右与设置到一个特定的许对象中。
with (expression) statement;
定义with语句的目的主要是为了简化多次编写同一个对象的工作,
var qs = location.search.substring(1);
var hostName = location.hostname;
var url= location.href;


<!DOCTYPE html>
<html>
<head>
    <title>With Statement Example 1</title>
    <script type="text/javascript">
   
        with(location){
            var qs = search.substring(1);
            var hostName = hostname;      //unavailable when viewing from a local file
            var url = href;
        }
        alert(qs);
        alert(hostName);
        alert(url);
    </script>
</head>
<body>
</body>
</html>
注意:
严格模式下不允许使用with 语句,否则视为语法错误。
由于大量使用with会导致性能下降,同时也给调试代码造成困难。

5)switch
JS的switch语句有自己的特色,
首先,可以在switch语句中使用任何数据类型(很多其他语言中只能使用数值)。
其次,每个case的值不一定是常量,也可以是变量,真实值表达式。
switch语句在比较值时使用的是全等操作符,因此不会发生类型转换

5、函数
1)用function关键字来声明
2)ECMAScript 的函数在定义是 不必指定是否返回值。实际上,任何函数在任何时候都可以通过return语句后跟要返回的值来实现返回值。return语句也可以不带有任何返回值,将返回undefined.
推荐的做法是:要么让函数始终都返回一个值,要么永远都不要返回值。否则,如果函数有时候返回,有时候不返回,会给调试代码带来不便。
3)严格模式对函数的限制
不要把函数或者参数命名为eval 或 arguments。
不要出现两个命名参数同名的情况
4)理解参数
ECMAScript 函数不介意传递进来多少参数,在不在乎什么数据类型。因为ECMAScript 中的参数在内部使用一个数组来表示的,在函数体内可通过arguments对象来访问这个数组。arguments[0]是第一个元素arguments.length属性,可以获知有多少个参数传递给了函数。对于arguments的行为,还有一点,就是它的值永远与对应命名参数的值同步。
    <script type="text/javascript">
        function doAdd(num1, num2) {
            if(arguments.length == 1) {
                alert(num1 + 10);
            } else if (arguments.length == 2) {
                alert(arguments[0] + num2);
            }
        }
       
        doAdd(10);        //20
        doAdd(30, 20);    //50
    </script>

    <script type="text/javascript">
        function doAdd(num1, num2) {

                arguments[1] = 10;

            alert(arguments[0] + num2);
        }
        doAdd(10, 20);        //20
        doAdd(30, 20);    //40
    </script>


注意:ECMAScript 中的所有参数传递的都是值,不可能通过引用传递参数。
函数没有重载,如果出现两个名字相同的函数,则该名字只属于后定义的函数。
示例:
    <script type="text/javascript">
        function addSomeNumber(num){
            return num + 100;
        }
       
        function addSomeNumber(num) {
            return num + 200;
        }
       
        var result = addSomeNumber(100);    //300
        alert(result);
    </script>

转载于:https://my.oschina.net/sosly/blog/630452