JavaScript高级程序设计(第三版)学习笔记20、21、23章

第20章,JSON

JSON(JavaScript Object Notation,JavaScript对象表示法),是JavaScript的一个严格的子集。

JSON可表示一下三种类型值:

简单值:字符串,数值,布尔值,null,不支持js特殊值:undefined

对象:一组无序的键值对

数组:一组有序的值的列表

不支持变量,函数或对象实例

注:JSON的字符串必须使用双引号,这是与JavaScript字符串最大的区别

对象

{
     "name":"Nicholas",
     "age":20
}

注:JSON中的对象要求给属性加引号

与JavaScript不同,没有生命变量,末尾不用分号

对象嵌入:

{
    "name":"Nicholas",
    "age":19,
    "school":{
        "name":"school",
        "location":"location"
    }
}

数组

采用js的数组字面量形式:

[21,"hi",true]

注:JSON数组也没有分号和变量

数组嵌入

[
    {
        "title":"array",
        "author":"author"
    },
    [
        "title":"book",
        "author":{
            "nameOne",
            "nameTwo"
        }
    ]
]

JSON对象

早期的JSON解析器基本上使用的是js的eval函数。ECMAScript5定义了全局对象JSON,支持的浏览器:IE8+,Firefox3.5+,Safari4+,Chrome,Opera10.5+。

JSON对象的两个方法:stringify,parse。最简单情况,分别用于把js对象序列化为JSON字符串和把JSON字符串解析成原生js值

var book = {
    title:"title",
    author:[
        "Nicholas C. Zakas"
    ],
    edition:3,
    year:2011
};
var jsonText = JSON.stringify(book);
alert(jsonText);          //{"title":"title","author":["Nicholas C. Zakas"],"edition":3,"year":2011}

注:默认情况下JSON.stringify输出的JSON字符串不包含任何空格字符或缩进。

序列化时所有函数和原型成员都会被忽略,值为undefined的属性也会被跳过。

JSON.parse过程相反,传递的字符串不是有效JSON,会抛出错误

序列化选项

JSON.stringify还可以接收另外两个参数:1、过滤器,可以是数组,也可以是函数。2、选项,表示是否在JSON字符串保留缩进

1、过滤结果

若过滤器是数组,则JSON.stringify结果将只包含数组列出的元素

var book = {
    title:"title",
    author:[
        "Nicholas C. Zakas"
    ],
    edition:3,
    year:2011
};
var jsonText = JSON.stringify(book,["title","edition"]);     //{"title":"title","edition":3}

如果是函数,则又有不同

var jsonText = JSON.stringify(book,function(key,value){
    switch(key){
        case "author":
            return value.join(",");

        case "year":
            return 5000;

        case "edition":
            return undefined;
        default:
            return value;
    }
});                                   //{"title":"title","author":"Nicholas C. Zakas","year":5000}

2、字符串缩进

JSON.stringify第三个参数用于控制缩进和空白符,若是数值,表示每个级别的缩进空格数

var jsonText = JSON.stringify(book,null,4);
//结果:
{
    "title": "title",
    "author": [
        "Nicholas C. Zakas"
    ],
    "edition": 3,
    "year": 2011
}

注:最大缩进空格数为10,大于10的数值全部转为10

若缩进参数是字符串,则将被用于缩进字符

{
- -"title": "title",
- -"author": [
- - - -"Nicholas C. Zakas"
- -],
- -"edition": 3,
- -"year": 2011
}

注:最大缩进字符数不能超过10,超过的将只显示前10个字符

3、toJSON方法

toJSON方法可以作为函数过滤器的补充,理解序列化顺序:

1、如果存在toJSON方法,而且能通过它取得有效值,调用该方法,否则返回对象本身

2、若提供了第二个参数,应用这个函数过滤器,传入函数过滤器的值是第一步返回值

3、对第二步返回值进行序列化

4、若提供了第三个参数,执行相应格式化

解析选项

JSON.parse也接收另一个参数,是一个函数,将在每个键值对上调用。若返回结果为undefined,表示删除该值,返回其他值,则将该值插入到结果。

var book = {
    title:"title",
    author:[
        "Nicholas C. Zakas"
    ],
    edition:3,
    year:2011,
    releaseDate:new Date(2011,11,1)
};

var jsonText = JSON.stringify(book);
var bookCopy = JSON.parse(jsonText,function(key,value){
    if(key == "releaseDate"){
        return new Date(value);
    }else{
        return value;
    }
});

alert(bookCopy.releaseDate.getFullYear());               //2011

第21章,Ajax和Comet

Ajax核心是XMLHttpRequest对象,能够以异步的方式从服务器获取更多信息,意味着用户单击后,可以不必刷新页面也能取得数据

XMLHttpRequest

IE7+,Firefox,Opera,Chrome,Safari都支持原生的XHR对象,创建对象:

var xhr = new XMLHttpRequest();

浏览器兼容

function createXHR(){
    if(typeof XMLHttpRequest != "undefined"){
        return new XMLHttpRequest;
    }else if(typeof ActiveXObject != "undefined"){
        if(typeof arguments.callee.activeXString != "string"){
            var versions = ["MSXML2.XMLHttp.6.0","MSXML2.XMLHttp.3.0","MSXML2.XMLHttp"],i,len;
            for(i=0,len=versions.length;i < len;i++){
                try{
                    new ActiveXObject(versions[i]);
                    arguments.callee.activeXString = versions[i];
                    break;
                }catch(ex){
                    //跳过
                }
            }
        }
        return new ActiveXObject(arguments.callee.activeXString);
    }else{
        throw new Error("No XHR Object available");
    }
}
//使用示例
var xhr = createXHR();

XHR用法

第一个方法:open,接收3个参数:

1、要发送的请求的类型(“get”,“post”)

2、请求的URL

3、表示是否异步发送请求的布尔值

xhr.open("get","example.php",false);

说明:1、url相对于执行代码的当前页面(也可以使用绝对路径),2、并不会真正发送请求,而是启动一个请求以备发送

使用send方法发送:

xhr.send(null);

send接受一个参数:作为请求主体发送的数据,不需要则要传入null。响应的数据会被填充到XHR对象的属性。属性简介:

responseText:作为响应主体被返回的文本

responseXML:响应内容类型若是"text/xml"或"application/xml",将保存包含着响应数据的XML DOM文档

status:响应的HTTP状态

statusText:HTTP状态说明

接到响应后,首先检查status属性,可以将HTTP状态码200,作为成功的标志,状态码304表示请求资源并没有修改,可以直接使用浏览器中缓存的版本。

xhr.open("get","example.php",false);               //同步请求
xhr.send(null);

if((xhr.status >= 200 && xhr.status < 300) || xhr.status == 304){
    alert(xhr.resopnseText);
}else{
    alert("Request was unsuccessful: "+xhr.status);
}

异步请求,检查readyState属性,表示请求/响应过程的当前活动阶段,取值:

0:未初始化,尚未调用open

1:启动,已调用open,未调用send

2:发送,已调用send,未收到响应

3:接收,已接收部分数据

4:完成,接收全部数据,已经可以在客户端使用了

必须在调用open之前指定onreadystatechange事件处理程序才能确保跨浏览器兼容性:

var xhr = createXHR();
xhr.onreadystatechange = function(){                         //DOM0级方法,不是所有浏览器都支持DOM2级方法
    if(xhr.readyState == 4){
        if((xhr.status >= 200 && xhr.status < 300) || xhr.status == 304){
            alert(xhr.resopnseText);
        }else{
            alert("Request was unsuccessful: "+xhr.status);
        }
    }
};
xhr.open("get","example.php",true);                         //异步请求
xhr.send(null);

在接收到响应之前还可以调用abort方法来取消异步请求:

xhr.abort();

HTTP头部信息

默认情况下,发送XHR请求的同时,还会发送下列头部信息
Accept:浏览器能够处理的内容类型

Accept-Charset:浏览器能够显示的字符集

Accept-Encoding:浏览器能够处理的压缩编码

Accept-Language:浏览器当前设置语言

Connection:浏览器与服务器之间的链接类型

Cookie:当前页面设置的热河Cookie

Host:发出请求的页面所在的域

Referer:发出请求的页面的URI。注:HTTP规范把这个头部字段拼错了,应该是referrer

User-Agent:浏览器的用户代理字符串

以上列出的基本上是所有浏览器都会发送的。可以通过setRequestHeader方法设置自定义的请求头部信息。接收两个参数:头部字段名称,头部字段值,要成功发送请求头部信息,必须在调用open方法之后,调用send方法之前调用setRequestHeader

var xhr = createXHR();
xhr.onreadystatechange = function(){
    if(xhr.readyState == 4){
        if((xhr.status >= 200 && xhr.status < 300) || xhr.status == 304){
            alert(xhr.resopnseText);
        }else{
            alert("Request was unsuccessful: "+xhr.status);
        }
    }
};
xhr.open("get","example.php",true);
xhr.setRequestHeader("MyHeader","MyValue");
xhr.send(null);

调用XHR对象的getRequestHeader方法并传入头部字段名称,可以取得相应头部信息,调用getAllResponseHeaders()方法则可以获得一个包含所有头部信息的长字符串。

GET请求

使用GET请求经常发生的一个错误,就是查询字符串的格式有问题,查询字符串的每个参数的名称和值都必须使用encodeURIComponent()(第五章提到的通用资源标识符编码)进行编码,然后才能放到URL末尾,而且所有键-值对都必须使用和号(&)分隔。

POST请求

通常用于向服务器发送应该保存的数据,应该把数据作为请求的主体提交,可以包含非常多的数据,且格式不限。

若需要将页面中的表单数据进行序列化,然后通过XHR放到服务器,则可以使用14章的serialize函数来创建字符串:

function submitData(){
    var xhr = createXHR();
    xhr.onreadystatechange = function(){
        if(xhr.readyState == 4){
            if((xhr.status >= 200 && xhr.status < 300) || xhr.status == 304){
                alert(xhr.resopnseText);
            }else{
                alert("Request was unsuccessful: "+xhr.status);
            }
        }
    };

    xhr.open("post","postExample.php",true);
    xhr.setRequestHeader("Content-Type","application/x-www-form-urlencoded");
    var form = document.getElementById("user-info");
    xhr.send(serialize(form));
}

示例php文件:

<?php
    header("Content-Type:text/plain");
    echo <<<EOF
    Name:{$_POST[‘user-name‘]}
    Email:{$_POST[‘user-email‘]}
    EOF;
?>

如不设置Content-Type头部信息,要访问同样信息必须借助$HTTP_RAW_POST_DATA

XMLHttpRequest2级

定义FormData类型,为序列化表单以及创建与表单格式相同的数据(用于通过XHR传输)提供了便利。

方法1、

var data = new FormData();
data.append("name","Nicholas");          //接收两个参数:键,值

方法2、

var data = new FormData(document.forms[0]);     //直接使用表单元素

方法3、

var form = document.getElementById("user-info");
xhr.send(new FormData(form));

支持的浏览器:Firefox4+,Safari5+,Chrome,Android3+,WebKit

超时设定

IE8为XHR添加了timeout属性,表示请求等待多少毫秒之后终止,在写作JavaScript高级程序设计第三版时,IE8+仍然是唯一支持超时设定的浏览器

overrideMimeType方法

Firefox最早引入overrideMimeType方法,用于重写XHR响应的MIME类型。因为返回响应的MIME类型决定了XHR如何处理它。

支持的浏览器Firefox,Safari4+,Opera10.5,Chrome

进度事件

Progress Events规范是W3C的一个工作草案,定义了与客户端服务器通信有关的事件,最早针对XHR操作,目前也被其他API借鉴,6个进度事件:

loadstart:接收到响应数据第一个字节触发

progress:接收响应期间持续不断地触发

error:请求错误触发

abort:调用abort方法触发

load:接收到完整的响应数据触发

loadend:通信完成或触发error,abort,load事件后触发

跨源资源共享

IE对CORS的支持

CORS(Cross-Origin Resource Sharing,跨源资源共享)是W3C的一个工作草案

IE8中引入了XDR(XDomainRequest)类型,与XHR类似,但能实现安全可靠的跨域通信。与XHR不同:

1、cookie不会随请求发送,也不会随请求返回

2、只能设置头部信息中的Content-Type

3、不能访问响应头部信息

4、只支持GET和POST请求

使用方法,也是创建一个XDomainRequest实例,调用open,调用send,open方法只接受两个参数,请求类型,URL。所有请求都是异步。

其他浏览器对CORS的支持

Firefox3.5+,Safari4+,Chrome,ios版Safari,Android平台中的WebKit都通过XHR对象实现了对CORS的原生支持。

限制:

1、不能使用setRequestHeader

2、不能发送和接收cookie

3、调用getAllResponseHeaders会返回空字符串

其他跨域技术

图像ping

JSONP

Comet

Comet一种更高级的Ajax技术。Ajax是从页面向服务器请求数据的技术,Comet是服务器向页面推送数据的技术。能够让信息近乎实时的被推送到页面上。

服务器发送事件

SSE(Server-Sent Events,服务器发送事件)是围绕只读Comet交互推出的API或者模式

Web Socket

使用标准的HTTP服务器无法实现Web Socket,只有支持这种协议的专门服务器才能工作。

支持浏览器:Firefox6+,Safari5+,Chrome,ios4+版Safari

1、Web Socket API

要创建Web Socket,先实例一个WebSocket对象并传入要连接的URL

var socket = new WebSocket("ws://www.example.com/server.php");

注:必须传入绝对URL

表示当前状态的readyState属性:

WebSocket.OPENING(0):正在建立连接

WebSocket.OPEN(1):已建立连接

WebSocket.CLOSING(1):正在关闭连接

WebSocket.CLOSE(3):已关闭

关闭Web Socket连接:

socket.close();

2、发送和接收数据

socket.send("hello world");          //任意字符串

只能发送纯文本数据,发杂结构的数据要经过序列化。

3、其他事件

open:成功建立连接触发

error:发生错误触发,连接不能持续

close:连接关闭触发

第23章,离线应用与客户端存储

离线检测

H5定义了navigator.onLine属性,true表示能上网。

H5还定义了两个事件:online(离线变在线触发),offline(在线变离线触发),在window对象上触发。

应用缓存

要在缓存中保存数据,可以使用描述文件

数据存储

HTTP Cookie,通常叫做cookie。

1、限制

在性质上是绑定在特定域名下的。

2、cookie的构成

cookie由浏览器保存的以下几块信息构成

名称:唯一确定cookie的名称,不缺分大小写,实践中最好看成区分大小写。

值:储存在cookie中的字符串值,必须被URI编码

域:对于哪个域有效

路径:对于域中的那个路径,应该向服务器发送cookie

失效时间:cookie应该被删除的时间

安全标志:指定后,cookie只有在使用ssl连接时才发送到服务器

3、js中的cookie

在js中处理cookie有些复杂,因为众所周知的蹩脚的接口,即BOM的document.cookie属性

基本的cookie操作:读,写,删,在CookieUtil对象表示:

var socket = new WebSocket("ws://www.example.com/server.php");
var CookieUtil = {
    get:function(name){
        var cookieName = encodeURIComponent(name) + "=" ,
            cookieStart = document.cookie.indexOf(cookieName),
            cookieValue = null;

        if(cookieStart > -1){
            var cookieEnd = document.cookie.indexOf(";",cookieStart);
            if(cookieEnd == -1){
                cookieEnd = document.cookie.length;
            }
            cookieValue = decodeURIComponent(document.cookie.substring(cookieStart+cookieName.length,cookieEnd));
        }

        return cookieValue;
    },
    set:function(name,value,expires,path,domain,secure){
        var cookieText = encodeURIComponent(name) + "=" + encodeURIComponent(value);

        if(expires instanceof Date){
            cookieText += "; expires=" + expires.toGMTString();
        }
        if(path){
            cookieText += "; path=" + path;
        }
        if(domain){
            cookieText =+ "; domain=" + domain;
        }
        if(secure){
            cookieText += "; secure=" + secure;
        }
        document.cookie = cookieText;
    },
    unset:function(name,path,domain,secure){
        this.set(name,"",new Date(0),path,domain,secure);
    }
};

使用示例:

//设置cookie
CookieUtil.set("name","Nicholas");
CookieUtil.set("book","Professional JavaScript");

//读取
alert(CookieUtil.get("name"));  //"Nicholas"
alert(CookieUtil.get("book"));  //Professional JavaScript

//删除
CookieUtil.unset("name");
CookieUtil.unset("book");

//设置cookie,包括它的路径、域、失效日期
CookieUtil.set("name","Nicholas","/books/projs","www.wrox.com",new Date("January 1,2010"));

//删除刚设置的cookie
CookieUtil.unset("name","/books/projs","www.wrox.com");

//设置安全cookie
CookieUtil.set("name","Nicholas",null,null,null,true);

4、子cookie

为了绕开浏览器的单域名下cookie数量限制

5、关于cookie的思考

尽量少存储信息,不存敏感信息

Web存储机制

Web Storage目的是克服由cookie带来的一些限制。主要目的:

1、提供一种cookie之外存储会话数据的途径;

2、提供一种存储大量可以跨会话存在的数据的机制

Web Storage包含了两种对象定义:sessionStorage,globalStorage,支持浏览器:IE8+,Firefox3.5+,Chrome4+,Opera10.5+

1、Storage类型

注:Storage类型只能存字符串,不是字符串的会被转换成字符串

2、sessionStorage对象

数据值保存到浏览器关闭

3、globalStorage对象

目的:跨越会话存储数据,有特定的访问限制。

数据保留到js删除或用户清除浏览器缓存

4、localStorage对象

要访问同一个localStorage对象,页面必须来自同一域名(子域名无效),使用同一种协议,在同一个端口

数据保留到js删除或用户清除浏览器缓存

5、storage事件

对Storage对象的任何修改,都会在文档上触发storage事件

IndexedDB

在浏览器中保存结构化数据的一种数据库

操作完全异步

1、数据库

open方法,存在就打开,不存在就创建并打开

2、对象存储空间

3、事务

4、使用游标查询

在对象存储空间调用openCursor方法卡创建游标

5、键范围

通过游标查找方式有限,键范围为游标增添了灵活性

6、设定游标方向

7、索引

8、并发问题

9、限制

与Web Storage类似,只能由同源(同协议,域名,端口)页面操作,不能跨域共享信息。

空间限制

时间: 2024-10-22 07:19:25

JavaScript高级程序设计(第三版)学习笔记20、21、23章的相关文章

javascript高级程序设计第三版 读书笔记

第三章   基本概念 1.在JavaScript中是区分大小写的,第一个字符是字母 _ 或者$,其他字符可以试数字 字母 _ 或者$,命名格式要求是驼峰式书写(第一个字母小写,剩下的每个有意义的单词开头大写  比如fontSize) 2.单行注释//  块级注释为/*多行 内容*/ 不得使用关键字和保留字 3.在JavaScript中变量是松散型的   可以为任何一种类型 4.用var操作符定义的变量成为定义该变量的作用域中的局部变量. function test(){ var i = 'hi'

《JavaScript高级程序设计 第三版》 前2章 Javascript简介与HTML 读书笔记

第一章:Javascript简介 1.JavaScript诞生于1995年,当时,它的主要目的是处理以前由服务器端语言(如Perl)负责的一些输入验证操作.现在,JavaScript是一种专为与网页交互而设计的脚本语言. 注:Netscape(网景)公司研发,Java是sun公司研发,原名为LiveScript,为了搭上媒体热炒的Java的顺风车,更名为JavaScript 2.微软推出JSript的和网景的JavaScript相竞争,最后微软胜利.ECMA指定了规定并重新命名为ECMAScri

javascript高级程序设计第三版dom元素大小笔记

是滚动大小(scroll dimension),指的是包含滚动内容的元素的大小.有些元素(例如 <html>元素),即使没有执行任何代码也能自动地添加滚动条:但另外一些元素,则需要通过 CSS 的 overflow 属性进行设置才能滚动.以下是 4 个与滚动大小相关的属性. 在IE8以下scrollHeight=元素内容本身的高度. 1.增加边框,不同浏览器有不同解释. 谷歌火狐IE>=8会忽略边框的大小. 2,增加内边距,最终值是width||height+padding ie8以下是

2.1 &lt;script&gt;元素【JavaScript高级程序设计第三版】

向 HTML 页面中插入 JavaScript 的主要方法,就是使用<script>元素.这个元素由 Netscape 创造并在 Netscape Navigator 2 中首先实现.后来,这个元素被加入到正式的 HTML 规范中. HTML 4.01 为<script>定义了下列 6 个属性. async:可选.表示应该立即下载脚本,但不应妨碍页面中的其他操作,比如下载其他资源或等待加载其他脚本.只对外部脚本文件有效. charset:可选.表示通过 src 属性指定的代码的字符

21.1 XMLHttpRequest 对象【JavaScript高级程序设计第三版】

IE5 是第一款引入XHR 对象的浏览器.在IE5 中,XHR 对象是通过MSXML 库中的一个ActiveX对象实现的.因此,在IE 中可能会遇到三种不同版本的XHR 对象,即MSXML2.XMLHttp.MSXML2.XMLHttp.3.0 和MXSML2.XMLHttp.6.0.要使用MSXML 库中的XHR 对象,需要像第18章讨论创建XML 文档时一样,编写一个函数,例如: //适用于IE7 之前的版本 function createXHR() { if (typeof argumen

20.2 解析与序列化【JavaScript高级程序设计第三版】

JSON 之所以流行,拥有与JavaScript 类似的语法并不是全部原因.更重要的一个原因是,可以把JSON 数据结构解析为有用的JavaScript 对象.与XML 数据结构要解析成DOM 文档而且从中提取数据极为麻烦相比,JSON 可以解析为JavaScript 对象的优势极其明显.就以上一节中包含一组图书的JSON数据结构为例,在解析为JavaScript 对象后,只需要下面一行简单的代码就可以取得第三本书的书名: books[2].title 当然,这里是假设把解析JSON 数据结构后

模拟事件【JavaScript高级程序设计第三版】

事件,就是网页中某个特别值得关注的瞬间.事件经常由用户操作或通过其他浏览器功能来触发.但很少有人知道,也可以使用JavaScript 在任意时刻来触发特定的事件,而此时的事件就如同浏览器创建的事件一样.也就是说,这些事件该冒泡还会冒泡,而且照样能够导致浏览器执行已经指定的处理它们的事件处理程序.在测试Web 应用程序,模拟触发事件是一种极其有用的技术.DOM2 级规范为此规定了模拟特定事件的方式,IE9.Opera.Firefox.Chrome 和Safari 都支持这种方式.IE 有它自己模拟

4.1 基本类型和引用类型的值【JavaScript高级程序设计第三版】

ECMAScript 变量可能包含两种不同数据类型的值:基本类型值和引用类型值.基本类型值指的是简单的数据段,而引用类型值指那些可能由多个值构成的对象. 在将一个值赋给变量时,解析器必须确定这个值是基本类型值还是引用类型值.第3 章讨论了5 种基本数据类型:Undefined.Null.Boolean.Number 和String.这5 种基本数据类型是按值访问的,因为可以操作保存在变量中的实际的值. 引用类型的值是保存在内存中的对象.与其他语言不同,JavaScript 不允许直接访问内存中的

10.1.5 Comment类型【JavaScript高级程序设计第三版】

注释在DOM中是通过Comment 类型来表示的.Comment 节点具有下列特征: nodeType 的值为8: nodeName 的值为"#comment": nodeValue 的值是注释的内容: parentNode 可能是Document 或Element: 不支持(没有)子节点. Comment 类型与Text 类型继承自相同的基类,因此它拥有除splitText()之外的所有字符串操作方法.与Text 类型相似,也可以通过nodeValue 或data 属性来取得注释的内

读Javascript高级程序设计第三版第六章面向对象设计--创建对象

虽然Object构造函数或者对象字面量都可以用来创建单个对象,但是缺点非常明显:使用同一接口创建很多对象,会产生大量重复代码. 工厂模式  1 function CreatePerson(name,age,job){ 2         var o=new Object(); 3         o.name=name; 4         o.age=age; 5         o.job=job; 6         o.sayName=function(){ 7