BOM-浏览器对象模型

BOM提供了很多对象,用于访问浏览器的功能,这些功能与任何网页内容无关。W3C为了把浏览器中JavaScript最基本的部分标准化,已经将BOM的主要方面纳入了HTML5的规范中。

window对象

BOM的核心对象时window,它表示浏览器的一个实例。在浏览器中,window对象有双重角色,它既是通过JavaScript访问浏览器窗口的一个接口,又是ECMAScript规定的Global对象。

  1. 所有在全局作用域中声明的变量、函数都会变成window对象的属性和方法。后面的很多全局JavaScript对象(location和navigator)实际上都是window对象的属性。
  2. 如果页面中包含框架(frame),则每个框架都拥有自己的window对象。在使用框架的情况下,浏览器中会存在多个Global对象,每个框架中定义的全局变量会自动成为框架中window对象的属性。
  3. IE、Safari、Oprea、Chrome使用screenLeft和screenTop属性表示窗口相对屏幕左边和上边的位置;Firefox则使用screenX和screenY属性,Safari和chrome也支持这个属性。使用moveTo()和moveBy()也可以将窗口精确地移动到一个新位置。这些属性和方法与使用的浏览器有很大的关系。
  4. 使用window.open()方法既可以导航到一个特定的URL,也可以打开一个新的浏览器窗口。这个方法接收4个参数:要加载的URL、窗口目标、一个特性字符串以及一个表示新页面是否取代浏览器历史记录中当前加载页面的布尔值。
  5. JavaScript是单线程语言,但它允许通过设置超时值和间歇时间值(一般不使用)来调度代码在特定的时刻执行。setTimeout(function(){},1000),延迟一秒
  6. 系统对话框:浏览器通过alert()、confirm()、prompt()来调用警告、确认、提示框。
    1
    2
    3
    4
    5
    6
    alert("hello world!"); //一个OK
    confirm("are you sure?"); //一个OK,一个Cancel
    prompt("what is your name?","Michael"); //OK Cancle 和一个默认为Michael的输入框

    window.print(); //显示“打印”对话框
    window.find(); //显示“查找”对话框

location对象

location是最有用的BOM对象之一,它提供了与当前窗口中加载的文档有关的信息,还提供了一个写导航功能。它既是window对象的属性,也是document对象的属性。

属性名 例子 说明
hash “#contents” 返回URL中的hash
host “www.wrox.com:80” 返回服务器名和端口号
hostname “www.wrox.com” 不带端口号的服务器名
href http://www.wrox.com 加载页面的完整的URL
pathname “/WileCDA/“ URL中的目录和文件名
port “8080” URL中指定的端口号
protocol “http:” 页面使用的协议
search “?q=javascript” URL的查询字符串
  • 查询字符串参数:根据location的serch方法获取查询字符串,根据&来分割字符串,再将相应的参数和值放入args数组中,就可以方便对每个参数进行访问了。
  • 通过location.assign(“http://www.wrox.com“) 可以立即打开新URL。此外通过window.location和location.href(常用)也可以达到上面的效果。还可以通过修改location的hash、search等属性进而修改location。

navigator对象现在已经成为识别客户端浏览器的事实标准。navigator对象时所有支持JavaScript的浏览器所共有的,但是每个浏览器的navigator对象也都有一套自己的属性。
对于非IE浏览器,可以使用navigator对象的plugins数组来检车插件。navigator.plugins[n]即保存了插件。if(navigator.plugins[i].name.toLowerCase().indexOf(name)>-1)即便是存在名称为name的插件。

客户端检测

面对普遍存在的浏览器的不一致性问题,开发人员要么采取迁就各方的“最小公分母”策略,要么(也是最常见的)利用各种客户端检测方法,来突破或者规避种种局限性。检测Web客户端的手段很多,而且各有利弊。但不到万不得已,不要使用客户端检测,应该优先使用更通用的方法。一言以蔽之,先设计最通用的方案,然后再使用特定于浏览器的技术增强方案。

能力检测

最常用也最为人们广泛接受的客户端检测形式是能力检测。其目标不是识别特定的浏览器,而是识别浏览器的功能。能力检测不是浏览器检测,所以不能根据能力检测判断浏览器为何种浏览器。在可能的情况下,尽量采用typeof进行能力检测。例如:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
//简单的能力检测
function getElement(id){
if(document.getElementById){
return document.getElementById(id);
}else if(document.all){
return document.all[id];
}else{
throw new Error("no way to retrieve element");
}
}

//使用typeof检测。要检测具体的要使用的属性方法是否存在
function isSortable(object){
return typeof object.sort == "function";
}

怪癖检测

与能力检测类似,怪癖检测的目标是识别浏览器的特殊行为。通常需要运行一小段代码,一确定某一特性不能正常工作。一般来说,“怪癖”是个别浏览器所独有的,而且通常被归为bug。

用户代理检测

用户代理检测通过检测用户代理字符串来确定实际使用的浏览器,包括浏览器、平台、操作系统以及浏览器版本。在每一次HTTP请求过程中,用户代理字符串是作为响应首部发送的,而且该字符串可以通过JavaScript的navigator.userAgent属性访问。在服务器端,通过检测用户代理字符串来确定用户使用的浏览器是一种常见而且广为接受的做法。而在客户端,用户代理检测一般被当做一种万不得才用的做法,其优先级排在能力检测和怪癖检测之后。

闭包

闭包是指有权访问另一个函数作用域中的变量的函数。

闭包示例

  • 在匿名函数从createComparisonFunction()中被返回后,它的作用域链被初始化为包含createComparisonFunction()函数的活动对象和全局变量对象,匿名函数就可以访问其中定义的所有变量。
  • createComparisonFunction()函数执行完毕后,其执行环境的作用域链会被销毁,但其活动对象不会被销毁,因为匿名函数的作用域链仍然在引用这个活动对象。
  • 直到匿名函数被销毁后,createComparisonFunction()的活动对象才会被销毁。
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
function createComparisonFunction(propertyName){
returne function( object1, object2){
var value1 = boject1[propertyName];
var value1 = boject1[propertyName];

if(value1 < value2){
return -1;
}else if(value1 > value2){
return 1;
}else{
return 0;
}
}
}
//创建函数,并调用函数。
var compareNames = createComparisonFunction("name");
var result = compareNames({name:'liming'},{name:'zhao'});
//接触对匿名函数的引用,以便释放内存
compareNames = null;
  • 注意。闭包只能取得包含函数中任何变量的最后一个值,因为闭包所保存的是整个变量对象。
  • 在闭包中使用this对象很可能会出问题,this可能指向window。
  • 内存泄露。闭包中不使用包含函数的对象,会造成其占用的内存永远不会被回收。在包含函数中,使用的对象,最后设置为null。收回对象占用的大量内存。

模仿块级作用域

创建并立即调用一个函数,这个既可以执行其中的代码,又不会再内存中留下对该函数的引用,这就是模仿块级作用域。一般用于限制向全局作用域中添加过多的变量和函数。

1
2
3
4
5
6
7
8
9
function outputNumbers(count){
(function(){
for(var i=0; i < count; i++){
alert(i);
}
})();

alert(i); //会导致错误
}

私有变量

严格来说,JavaScript中没有私有成员的概念。不过任何在函数中定义的变量,都可以认为是私有变量。利用私有和特权成员,可以隐藏那些不应该被直接修改的数据。例如:

1
2
3
4
5
6
7
8
function Person(name){
this.getName = function(){
return name;
}
this.setName = function(value){
name = value;
}
}

面向对象

面向对象的语言有一个标志,那就是他们都有类的概念,而通过类可以创建任意多个具有相同属性和方法的对象。然而,ECMAScript中没有类的概念,所以它的对象也与基于类的语言中的对象有所不同。ECMA-262把对象定义为:“无序属性的集合,其属性可以包含基本值、对象或者函数”。

创建对象

在没有类的情况下,ECMAScript可以采用工厂模式、构造函数模式或者原型模式创建对象。

工厂模式

1
2
3
4
5
6
7
8
9
10
functiong createPerson(name,age){
var 0 = new Object();
o.name = name;
o.age = age;
o.sayName = funciont(){
alert(this.name);
};
return o;
}
var person1 = createPerson("liming", 20); //person1的类型为object

工厂模式虽然解决了创建多个相似对象的问题,但却没有解决对象识别的问题,即怎么知道一个对象的类型。

构造函数模式

由于工厂模式没有解决对象识别的问题,所以可以采用构造函数模式来做。但是构造函数模式的每个成员无法得到复用,包括函数。不能在多个对象间共享函数。

1
2
3
4
5
6
7
8
function Person(name,age){
this.name = name;
this.age = age;
this.sayName = funchion(){ //每次都会创建一个function的新实例
alert(this.name);
};
}
var person1 = new Person("liming",20);

原型模式

我们创建的每个函数都有一个prototype(原型)属性,这个属性时一个指针,指向一个对象,而对这个对象的用途是包含可以由特定类型的所有实例共享的属性和方法。

1
2
3
4
5
6
7
function Person(){}
Person.prototy.name = "liming";
Person.prototy.age = 20;
Person.prototy.sayName = function(){
alert(this.name);
}
var person1 = new Person(); //可以修改person1的属性

其他方法

除此以上三种基本方法外,还有结合几种方法产生的动态原型模式、寄生构造函数模式、稳妥构造函数模式等方法,分别有不同的优缺点。可根据需求选择相应的模式。

继承

许多OO语言都支持两种继承方式:接口继承和实现继承。由于函数没有签名,在ECMAScript中无法实现接口继承,所以主要依靠原形链来实现。原形链的构建是通过将一个类型的实例赋值给另一个构造函数的原型实现的,这样子类型就能够访问超类型的所有属性和方法。使用最多的继承模式是组成继承,这种模式使用原形链继承共享的属性和方法,而通过借用构造函数继承实例属性。除此外,还有原形链继承、寄生式继承、寄生组合式继承等方法。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
//此方法实现原型链的一种基本模式
function SuperType(){
this.property = true;
}

SuperType.prototype.getSuperValue = function(){
teturn this.property;
};

function SubType(){
this.subproperty = false;
}

//继承了SuperType
SubType.prototype = new SuperType();

SubType.prototype.getSubValue = function(){
return this.subproperty;
};

var instance = new SubType();
alert(instance.getSuperValue()); //true

引用类型

引用类型的值(对象)是引用类型的一个实例。在ECMAScript中,引用类型是一种数据结构,用于将数据和功能组织在一起。var person = new Object();,这行代码创建了Object引用类型的一个实例,然后该实例保存在变量person中。

Object类型

很多引用数据类型值都是Object类型的实例。而且,Object也是ECMAScript中使用最多的一个类型。 也可以使用对象字面量表示,省略“new object()”。一般来说,访问对象属性时都是用点表示:person.name,或方括号表示person[“name”](推荐使用)。

Array类型

ECMAScript中的数组与其他多数语言中的数组有着相当大的区别,虽然数组数据的有序列表,但数组的每一项都可以用来表示任何类型的数据。

数组的初始化

创建数据的基本方法由两种,第一种用Array构造函数,第二用使用数组字面量法。

1
2
3
4
5
6
7
8
9
var colors = new Array(20); //lenght = 20
var colors = Array("red","blue","green"); //可以不要new

var colors = ["red","blue","green"]
var values = [1,2,];//不要这样!会创建一个包含2或3项的数组

var values = [1,"two"]; //可以类型不同

var colors.length = 2; //会导致colors的长度变为2,去掉第三个及后面的数值

检测数组及转换方法

1
2
3
4
5
6
7
if (Array.isArray(value)) {//检查value是数组的话,执行操作}

alert(colors); //red,blue,green
alert(colors.toString()); //red,blue,green
alert(colors.valueOf()); //red,blue,green

alert(colors.join("||")); //red||blue||green

队列方法和栈方法

栈是先入后出策略,结合push()和pop()方法实现。队列是先入先出策略,结合push()和shift()方法实现。push()、pop()、shift()使用后,都会改变数组长度。

1
2
3
4
5
6
var count = colors.push("black","white");

var item = colors.pop(); //pop是突然抛出的意思。弹出最后一项"white"
var item1 = colors.shift(); //shift是移动的意思,取出第一项

var count = colors.unshift("yellow","o"); //在数组最前面添加两项

RegExp类型

ECMAScript通过RegExp类型支持正则表达式。使用下面类似Perl的语法,就可以创建一个正则表达式。

1
var expressions = /pattern/ flags ; //

模式pattern可以是任何简单或复杂的正则表达式,可以包含字符类、限定符、分组、向前查找以及反向引用。flags有三个标志g i m,分别表示全局模式、不区分大小写、多行模型。一次可以带多个标志。

Function类型

在ECMAScript中,函数都是Function类型的实例,与其它类型一样具有属性和方法,函数名实际上也是一个纸箱函数对象的指针,不会和某个函数绑定。函数名为指针,所以没有重载,后面的函数会指向之前定义的函数。另外,函数还可以作为值使用,它的值为返回值,所以可以作为另一个函数的输入参数。

函数声明与函数表达式

1
2
3
4
5
6
7
8
9
alert(sum(10,10)); //20.代码执行前,解析器已经将函数声明添加到函数声明中。
function sum(num1,num2){
return num1 + num2;
}

alert(sum1(10,10)); //错误!在执行前,变量sum中不会保存对函数的引用。因为函数在初始化语句中。
function sum1(num1,num2){
return num1 + num2;
}

函数内部属性

在函数内部,有两个特殊的对象:arguments和this。arguments是一个类数组对象,包含传入函数中的所有参数(函数可以传入任何数量的参数)。arguments月还有一个名叫callee的属性,它指向拥有这个arguments的函数。还有一个函数对象的属性:caller,保存着调用当前函数的函数的引用,如果实在全局作用域中调用当前函数,它的值是null。

1
2
3
4
5
6
7
function factorial(num){ // 使用递归算法求阶乘
if(num<=1){
return 1;
}else{
return nume*arguments.callee(num-1)
}
}

函数属性和方法

在ECMAScript中,函数是对象,因此函数也有属性和方法。每个函数都包含两个属性:length和prototype。length属性表示函数希望接收的命名参数的个数。prototype是保存所有实例方法的真正所在,比如toString()等方法都在prototype名下,只不过通过各自对象的实例访问本罢了。并且prototype属性不可枚举。

基本包装类型

为了便于操作基本类型值,ECMAScript还提供了3个特殊的引用类型:Boolean、Number、String。每当读取一个基本类型值的时候,后台就会创建一个对应的基本包装类型的对象。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
var falseObjext = new Boolean(false); //bool形式的false。但是用typeof返回时object
var falsevalue = false; //bool形式的false。使用typeo返boolean

var numberObject = new Number(10); // typeof返回object
var numberValue = 10; //typeof 返回number 两者的区别还在于对象的生存期。前者一直保存在内存中。后者不然
alert(numberValue.toString(16)); //“a”,转为16进制,再转换成字符串形式

var stringObject = new String("hello world"); //typeof :object。可以添加属性和方法。
var stringValue = "hello world"; //typeof: string 。这种方法不能为其添加属性方法,会被立即销毁
alert(stringValue.lenght); //"11"
var result = stringValue.concat("!!!"); //result:"hello world!!!"
var str = stringValue.subString(2); //llo world
var str = stringValue.slice(3,8); //lo wo
alert(stringValue.indexOf("o")); //4.第一个o的位置。lastIndexOf("o"),最后一个o的位置

单体内置对象

由ECMAScript实现提供的、不依赖于宿主环境的对象,在程序执行前已经存在。内置对象有Object、Array和String等。还有:Global和Math

Global对象

所有在全局作用域中定义的属性和函数,都是全局对象的属性。不属于任何其他对象的属性和方法都是Global对象的属性和方法。

  • URI编码方法。encodURI()和encodeURIComponent()可以对URI进行编码,以便发给浏览器。前者主要用于整个URI,后者主要用于对URI的某一段进行编码。
  • eval()方法:就像一个完整的ECMAScript解析器。只接受一个参数,即要执行那个的代码的字符串。
  • window对象:Web浏览器将这个全局对象作为window对象的一部分加以实现。所以全局作用域中声明的所有变量和函数,都成为了window对象的属性。

Math对象

ECMAScript还未保存数学公式和信息提供了一个公共位置,即Math对象。

  • Math.E: 自然数对数的底数,及常量E。还有Math.PI等特殊值常量
  • min()/max():求输入的number中的最大值或最小值
  • Math.round():四舍五入为最接近的整数。
  • Math.random(): 返回大于等于0小于1的一个随机数

JavaScript基本概念

语法

ECMAScript的语法大量借鉴了C及其他类C语言的语法。

  • 区分大小写
  • 标识符,指变量、函数、属性的名字,或者函数的参数。第一个字符必须是字母、下划线或美元符号。其他字符可以为字母、下划线、美元符号和数字。按照惯例,第一个字母小写,其他每个单词的首字母大写。
  • 注释。//单行注释。/多行注释/
  • 严格模式。在脚本顶部添加“use strict”
  • 语句。每个语句以“;”结束,可以省略,但是一般不省略,以避免出错和增进代码的性能。使用花括号将多条语句组合到一个代码块中。

变量

  • ECMAScript的变量是松散类型的,即可以用来保存任何类型的数据。每个变量仅仅是一个用于保存值的占位符而已。
  • 定义变量时使用var操作符,后跟变量名。可以给一个变量先符值一个字符串,再赋值一个数字,但是不推荐。
  • 在函数中,用var操作符定义的变量是局部变量,在函数退出后会被销毁。然而如果省略var,定义的变量会成为全局变量(但是不推荐这种方法,很难维护,且在严格模式下回抛出错误)。

数据类型

ECMAScript中有5中简单数据类型:Undefined、Null、Boolean、Number、String,一种复杂数据类型:Object,其本质由一组无序的名值对组成。

typeof操作符

typeof是一个操作符而不是函数,所以不需要使用圆括号。另外调用typeof null会返回object。typeof返回的有:undefined、boolean、string、number、object、function

Undefined类型

这种类型只有一个值,即特殊的undefined。在使用var声明变量但未对其加以初始化时,这个变量的值就是undefined。使用typeof操作符时,对于未定义的变量也会返回undefined。

1
2
3
//var age
alert(typeof age);//返回undefined,因为知道变量没有声明(定义而未初始化时也会返回undefined)
alert(age);//产生错误,age未定义

Null类型

它也是只有一个值的数据类型,这个特殊值是null。如果定义的变量准备在将来用于保存对象,最好初始化为null。

Boolean类型

该类型只有两个字面值:true、false。与数字值不一样,即true不一定等于1,false也不一定等于0.要将一个值转换为对应的boolean值,可用转型函数Boolean(),至于返回的这个值是true还是false,取决于要转换值的数据类型及其实际值。

Number类型

这种类型使用IEEE754格式来表示整数和浮点数值。为支持各种数值类型,ECMA-262定义了不同的数值字面量格式。

  • 整数:基本的为十进制整数,数字前为0表示八进制,为0x表示十六进制整数。
  • 浮点数值。可以用小数点表示,也可以用e表示,即科学表示法。
  • 由于内存的显示,ECMAScript不能保存所有的数值。如果一个值超出了范围,会被转换为Infinity和-Infinity,表示正无穷和负无穷。
  • NaN,即非数值是一个特殊的数值,用来表示一个本来要返回数值的操作数未返回数值的情况(这样就不会抛出错误)。任何涉及NaN的操作都会返回NaN,但NaN不等于任何值,包括其本身.要判断一个参数是不是数值可以用isNaN()函数。

除此外,还有3个函数可以把非数值转换为数值:Number()、parseInt()、parseFloat(),第一个可以用于任何数据类型,另外两个专门用于把字符串转换为数值。如果是Boolean,true和false分别转换为0和1;如果是null,返回0;如果是undefined,返回NaN;如果是对象,先调用对象的valueof(),然后按照规则转换返回的值,如果返回的是NaN,再调用对象的toString()方法,按照规则转换返回的字符串值;如果为字符串,规则如下:

1
2
3
4
5
var num = Number("123"); //123
var num = Number("0123");//123,前导的零都会被忽略
var num = Number("0xf");//15,包含十六进制格式,转换为相同大小的十进制
var num = Number("");//0,为空字符串,则返回0
var num = Number("hello 123");//NaN,如果字符串中包含以上之外的字符,转换为NaN。

在将字符串转换为Number时,一般使用parseInt()/patseFloat()

1
2
3
4
5
6
7
8
9
10
var num = parseInt("123blue");   //123,
var num = parseInt(""); //NaN
var num = parseInt("070"); //56,八进制
var num = parseInt("0xf"); //15,十六进制
var num = parseInt("22.5"); //22
var num = parseInt("AF",16); //175,按十六进制解析

var num = parseFloat("0908.5"); //908.5
var num = parseFloat("3.15e7"); //32150000
var num = parseFloat("0xf"); //0

String类型

表示字符串,可以由双引号或单引号表示,将其他类型的数值转换为字符串可以用.toString()方法(如果有该方法。且可以赋参数,表示按多少进制转换)。还可以使用String()方法,如果值有.toString()则调用;如果值是null,则返回”null”;如果值是undefined,返回”undefined”;

object类型

ECMAScript中的对象其实就是一组数据和功能的集合。对象可以通过new操作符后跟要常见的对象类型的名称来创建。

1
var o = new Object();   //可以省略圆括号,但是不推荐

在ECMAScript中,Object类型是所有它的实例的基础。但ECMA-262中对象的行为不一定适用于JavaScript中的其他对象,比如宿主对象DOM和BOM都可能自定义对象,而不继承Object。Object的实例都具有以下属性和方法:

  • constructor:保存着用于创建当前对象的函数。对于前面的例子而言,构造函数就是Object()
  • hasOwnProperty(propertyName):用于检查给定的属性在当前对象实例中是否存在。prototypeName是字符串形式,比如”name”
  • isPrototypeOf(object):用于检查传入的对象是否是当前对象的原型
  • propertyIsEnumerable(propertyName):用于检查给定的属性是否能够使用for-in语句来枚举。
  • toLocaleString():返回对象的字符串表示,该字符串与执行环境的地区对应。
  • toString():返回对象的字符串表示
  • valueOf():返回对象的字符串、数值或布尔值表示。通常与toString()方法返回值相同。

操作符

ECMAScript操作符的与众不同之处在于,它们能够适用于很多值,例如字符串、数字值、布尔值,甚至对象。不过,在应用于对象时,相应的操作符通常会调用对象的valueOf()或toString()方法,以便取得可以操作的值。

  • 一元操作符:递增递减(++、–前置后置)、一元加和减(将非数值转换为数值,减则转换为负值)
  • 位操作符:NOT(按位非)、AND(按位与)、OR(按位或)、XOR(按位异或)、<<(左移)、>>(有符号右移)、>>>(无符号右移)
  • 布尔操作符:!(逻辑非)、 &&(逻辑与)、 ||(逻辑或)
  • 乘性操作符:*(乘法)、/(除法)、%(求模)
  • 加性操作符:+(加法,负无穷加正无穷等于NaN,有一个为字符串,则另一个也转换为字符串拼接)- (一个为NaN,则返回NaN;把字符串等操作数转换为数值)
  • 关系操作符:<、>、<=、>=、==、!=、===(全等,在比较之前不转换操作符)、!==(不全等。不转换)
  • 条件操作符:条件?操作1:操作2(条件成立,操作1;不成立,操作2)
  • 赋值操作符:*=、/=、%=、+=、-+、<<=、>>=
  • 使用逗号可以在一条语句中执行多个操作,如var num1 = 1, num2 = 2;

语句

if语句

1
2
3
4
5
6
7
if(i > 5){
alert('大于5');
}else if(i < 0){
alert("小于0");
}else{
alert("在0~5之间");
}

do-while语句、while语句

do-while为后测试循环语句,while为前测试循环语句

1
2
3
4
var i = 0;
do{
i += 2;
}while(i < 0); // 最后i等于2,在执行之后才会测试出口条件

for语句、for-in语句

1
2
3
4
5
6
7
8
9
10
11
12
for(var i = 0; i < 10; i++){
if(i % 3 == 0){
continue; //跳出本次循环,继续执行下次循环
}
if(i % 5 == 0){
break; //跳出循环。
}
}

for(var propName in window){
document.write(propName);
}

其他

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
start: for(var i = 0; i < 10 ; i++){
alert(i);
} //它是label语句,为代码添加标签。label:statement

with(location){
var qs = search.substring(1); //等同于:var qs = location.search.substring(1);
var hostName = hostname; //等同于:var hostName = location.hostname;
} //with语句,主要为了简化多次编写同一个对象的工作

switch(i){
case 10:
alert('10');
break;
case 20:
alert('20');
break;
default:
alert('other');
} //switch语句。case value: statement;break;default:statement;

函数

ECMAScript中的函数使用function关键字来声明,后跟一组参数以及函数体。

  • 函数无须指定返回值,可以通过return语句后跟要返回的值来实现返回值。return后的语句就不会再继续执行。
  • 参数:ECMAScript不介意传递多少个参数,即使定义了接收几个参数。ECMAScript中的参数用arguments数组表示,在函数体内可以通过arguments[]来访问参数数组。
  • ECMAScript函数没有重载。即如果定义了两个名字相同的函数,则该名字只属于后定义的函数。
    1
    2
    3
    4
    function doAdd( num1, num2) {//没有传递值的参数被自动赋予undefined
    arguments[1] = 10; //如果没有传递num2,设置的值不会反应到命名参数中。arguments的长度由传入的参数决定。严格模式下,arguments赋值无效。
    alert(num1 + num2); //传入了num2,num2的值就会被赋值10.
    }

JavaScript概述

JavaScript简史

JavaScript诞生于1995年,当时它的主要目的是在客户端做一些基本的输入验证操作。如今,JavaScript具备了域浏览器窗口及其内容等几乎所有方面交互的能力,能够处理复杂的额计算和交互,拥有了闭包、匿名(lambda)函数,甚至元编程等特性。

JavaScript实现

JavaScript由一下三个不同的部分组成:核心(ECMAScript)、文档对象模型、浏览器对象模型。这三个主要部分,在当前主流浏览器中都得到了不同程度的支持。所有浏览器对ECMAScript的支持都还不错,但对DOM的支持彼此相差比较多,对于纳入HTML5标准的BOM来说,都实现了某些众所周知的共同特性,但其他特性还是会因浏览器而异。

  • ECMAScript提供核心语言功能。这门语言本身并不包含输入和输出定义,Web浏览器只是其实现可能的宿主环境之一。
  • DOM,提供访问和操作页面内容的方法和接口。是负责制定web通信标准的W3C(万维网联盟)着手规划的,目前有DOM1级、DOM2级、DOM3级。不同的浏览器对DOM的支持程度不同,但是目前,支持DOM已经成为浏览器开发商的首要目标。
  • BOM,提供与浏览器交互的方法和接口。由于没有BOM标准可以遵循,因此每个浏览器都有自己的实现。现在HTML5致力于把很多BOM功能写入正式规范,BOM实现的细节有望朝着兼容性越来越高的方向发展。

在HTML中使用JavaScript

数据结构(C语言版)

数据结构概述

数据结构是一门研究非数值运算的程序设计问题中计算机的操作对象以及它们之间的关系和操作等等的学科。抽象数据类型由数据对象,数据对象关系集和基本操作集。

  • 数据:在计算机科学中指所有能输入计算机中并被计算机程序处理的符号的总称。
  • 数据元素:数据的基本单位,在计算机程序中通常作为一个整体进行考虑和处理。如一本书的数目信息为一个数据元素,而一个数据元素又有许多数据项组成。数据项是不可分割的最小单位。
  • 数据对象:性质相同的数据元素的集合,是数据的一个子集。
  • 数据结构:是相互之间存在一种或多种特定关系的数据元素的结合。通常有四种基本结构:集合、线性结构、树形结构、图状结构或网状结构。

算法

算法有5个重要特性:有穷性、确定性、可行性、输入、输出。
算法设计的要求有:正确性、可读性、健壮性、效率与低存储需求。
算法效率的度量:

  • 时间复杂度:一般情况下,算法中基本操作重复执行的次数是问题规模n的某个函数f(n),算法的时间度量记做T(n) = O(f(n)
  • 空间复杂度,本书空间复杂度作为算法所需存储空间的度量,记做S(n) = O(f(n))

线性表

线性表是最常用且最简单的一种数据结构。一个线性表是N个数据元素的有限序列。

线性表的顺序表示和实现

线性表的顺序表示指用一组地址连续的存储单元依次存储线性表的数据元素(如数组等)。假设有a1~an个元素顺序组成线性表,要在ai处添加/删除一个元素,则必须移动n-i个元素。则该算法移动元素次数的期望为(n-1)/2和n/2,则算法的时间复杂度是O(n)。

线性链表

  • 线性表的链式存储结构的特点是用一组任意的存储单元存储线性表的数据元素。每个数据元素称为一个结点,包含两个域:数据域、指针域。整个链表的存取必须从头指针开始,且最后一个结点的指针域为null
  • 循环链表是另一种形式的链式存储,其特点是表总最后一个结点指向第一个结点。
  • 双向链表,为克服单链表单向性的缺点,可利用双向链表,一个结点有两个指针域。

栈和队列

从数据结构看,栈和队列也是线性表,其特殊性在于栈和队列的基本操作是线性表操作的子集,是操作受限的线性表。

栈(注意递归问题)

栈是限定仅在表尾进行插入或删除操作的线性表。即后进先出。表尾端有其特殊含义,称为栈顶,表头端称为栈底。插入元素叫入栈,删除栈底元素叫做出栈。栈的应用为迷宫求解问题、表达式求值(寄存运算符栈、寄存操作数栈)、实现递归(如求二叉树深度、N!)等。

队列

队列是一种先进先出的线性表。允许插入的一端叫做队尾,允许删除的一端称为队首。常用于排队的情况。

  • 链队列,即用链表表示的队列,一个队列需要两个分别指向队头和队尾的指针。
  • 循环对列。在循环链表的基础上,加上队首指针和队尾指针。

字符串

字符串是由零个或多个字符组成的有限序列,一般即为s = 'a1a2a3……an'
字符串在机内有三种表示方法:

  • 定长顺序存储表示,对字符串长度有限制。类似于线性表的顺序存储结构,用一组地址连续的存储单元存储字符串的字符序列。
  • 堆分配存储表示,对字符串长度没有限制。特点是以一组地址连续的存储单元存放字符串序列,但其存储空间是程序执行过程中动态分配的。
  • 串的块链存储表示。

数组和广义表

数组

数组一旦被定义,它的维数和维界就不再改变,即结构中的数据元素个数和元素间的关系不再变动。除了结构初始化和销毁外,只能存取元素和修改元素值。

矩阵的压缩存储

在数值分析中,常出现一些阶数很高的矩阵,同时矩阵中有很多相同的元素或者零元素(即稀疏矩阵),为了节省存储空间,可以对这类矩阵进行压缩存储。即:为多个值相同的元只分配一个存储空间(0元不分配空间)。采用三元组(x,y,value)顺序表对矩阵进行压缩。

广义表

广义表是线性表的推广。广义表LS的定义是一个递归的定义,如:LS=(a1(a2(a3,a4,a5)))
广义表非空时,称第一个元素a1为LS的表头,称其余元素组成的表是LS的表尾。表头可能是原子,也可能是列表。由于广义表中的数据元素可以具有不同的结构,因此难以用顺序存储结构表示,通常采用链式存储结构,每个数据元素可以由一个结点表示。广义表需要两种结构的结点,原子结点和表结点。一个表结点可由三个域组成:标志域、指示表头的指针域和知识表尾的指针域。一个原子结点需要:标志域和值域。

树和二叉树

树型结构是一类重要的非线性数据结构。其中以树和二叉树最为常用。

树是n个结点的有限集,在任意一颗非空树中:1.有且仅有一个特定的称为根的结点。2.当n>1时,其余几点可分为m个互不相交的有限集,其中每个集合本身又是一棵树,并且被称为子树。结点拥有的子树数称为结点的度,度为0的根节点称为叶子或终端结点,不为0的结点称为非终端节点或分支结点。结点的子树的根称为该结点的孩子(child),该结点称为孩子的双亲(parent),同一个双亲的孩子之间称为兄弟(sibling)。树中结点的最大层次称为树的深度。根节点为第一层。
森林是m颗互不相交的树的集合。对树中每个结点而言,其子树的集合即为森林。

二叉树

二叉树是另一种树型结构,其特点是每个结点至多只有两颗子树,且二叉树的子树有左右之分,其次序不能任意颠倒。
一颗深度为k且有2的k次方减一个结点的二叉树称为满二叉树。从上到下,从左到右为满二叉树所有结点编号的称为完全二叉树。二叉树存储结构如下:

  • 顺序存储结构:仅适用于完全二叉树
  • 链式存储结构:二叉树的链表中的结点至少包含三个域:数据域和左右指针域,有时还要有双亲域。

遍历二叉树和线索二叉树

  • 遍历二叉树:按某条搜索路径巡访每个结点,且只访问一次。有先(根)序遍历、中序遍历和后序遍历。
  • 线索二叉树:对一个非线性结构进行线性化操作。一般链表存储结构为:左孩子指针域、数据、右孩子指针域。添加两个标志域:ltag、rtag。若结点有左子树,则ltag为0,lchild指示左孩子,否则,ltag为1,lchild指示前驱,若结点有右子树,则ltag为0,lchild指示右孩子,否则,ltag为1,lchild指示后继。

树和森林

树常用的存储结构:

  • 双亲表示法:每个结点中包含两项:数据和双亲结点指示。
  • 孩子表示法:每个结点可能有多棵树,则可用多重链表,即每个结点有多个指针域指向孩子。
  • 孩子兄弟表示法:又称二叉树表示法。链表中结点的两个链域分别指向该结点的每第一个孩子结点和下一个兄弟结点。

赫夫曼树及其应用

赫夫曼(Huffman)树,又称最优树,是一类带权路径长度最短的树,有着广泛的应用。带权路径长度可用wi*深度。

  • 构造赫夫曼树的方法为:选取两颗根节点的权值最小的树作为左右子树构造一颗新的二叉树。新的二叉树的根节点的权值为左右子树上根节点的权值之和。
  • 赫夫曼编码:利用以上方法构造二叉树,并对其编码。如A(0) B(10) C(110) D(111)

图中的数据元素称为顶点,两个顶点之间的关系称为弧,弧有方向就称图为有向图,否则称无向图。顶点的度是和此顶点关联的顶点的个数。图的存储结构有:

  • 数组表示法:n个顶点,则为n*n维数组,0表示无关系,1表示有关系。
  • 邻接表:对图中每个顶点建立一个单链表,指向该顶点指向的所有的其他顶点。
  • 十字链表和邻接多重表。

图的遍历分为:深度优先搜素、广度优先搜素

查找

查找表是由同一类型的数据元素构成的集合。查找表分为静态查找表(查找是否存在、检索特定元素的属性)、动态查找表(查找并添加/删除)。
关键字:可唯一标识一个记录。次关键字可识别若干记录。

静态查找表

  1. 顺序表的查找。顺序表指顺序表或线性链表。顺序查找为从表中最后一个记录开始,逐个进行查找。O(n)
  2. 有序表的查找。折半查找,类似于二叉树。O(logn)
  3. 静态树表的查找。每条记录的查找概率不相等,根据权重选择折半记录。
  4. 索引顺序表的查找。记录是分块存储的,通过索引记录表可到达相应的块,再通过顺序查找进行查找。

动态查找表

  1. 二叉排序树。左子树<根节点<右子树。可能出现二叉树左右严重不平衡。平均二叉树的平均查找长度和logn是等数量级的。
  2. 平衡二叉树。平衡因子为左子树的深度减去右子树的深度。所有结结点的平衡因子都应该是-1、0、1。保持平衡可以通过更改根节点来实现。O(logn)
  3. B-树和B+树
  4. 键树,又称数字查找树。

哈希表

在查找时,如果可以根据一个对应关系,找到给定值K的像f(K),则不需要进行比较便可以直接取得所查记录。这个关系f称为哈希函数,这种表称为哈希表。

哈希函数的构造方法有:直接定址法、数字分析法、平方取中法、折叠法、除留余数法、随机数法等。

内部排序

插入排序

  1. 直接插入排序:第i趟直接插入排序的操作为:在还有i-1个记录的有序子序列r[1……i-1]中插入一个记录r[i]以后,编程含有i个记录的有序子序列,插入位置查找的方法为从最大值/最小值开始进行依次判断。移动次数约为四分之n的平方。O(n2)
  2. 折半插入排序。仅减少了关键字间的比较次数,而记录的移动次数不变。O(n2)
  3. 2-路插入排序。是在折半插入的基础上再改进,即从两边排序。移动次数约为八分之n的平方。
  4. 表插入排序。使用链表,仅改变存储结构,不移动记录。O(n2)

  5. 希尔排序。先将整个待排记录分割为若干个子序列分别进行直接插入排序,待整个序列中的记录基本有序时,再对整体记录进行一次直接插入排序。它的时间是所取增量序列的函数,可以降低时间复杂度。

快速排序

  1. 起泡排序:左右比较,大的放后面,一轮下来,最大值排最后。依次可得次大值,最终得到排序序列。需进行n(n-1)/2次移动,并做等数量级的记录移动。O(n2)
  2. 快速排序是对起泡排序的一种改进。通过一趟排序,将待排数据分割成独立的两部分,在进行排序。分割方法可以为比第一个大的放右边,否则放左边。o(nlogn),并且被认为是在同数量级排序方法中,平均性能最好。

选择排序

  1. 简单选择排序法:把第一个数与其他所有数比较,获取最小值。然后排第二个……
  2. 树型选择排序、堆排序、归并排序等。

其他排序

归并排序、基数排序等

排序方法 平均情 最好情况 最坏情况 辅助空间 稳定性
冒泡排序 O(n^2) O(n) O(n^2) O(1) 稳定
选择排序 O(n^2) O(n^2) O(n^2) O(1) 不稳定
插入排序 O(n^2) O(n) O(n^2) O(1) 稳定
希尔排序 O(n*log(n))~O(n^2) O(n^1.3) O(n^2) O(1) 不稳定
堆排序 O(n*log(n)) O(n*log(n)) O(n*log(n)) O(1) 不稳定
归并排序 O(n*log(n)) O(n*log(n)) O(n*log(n)) O(n) 稳定
快速排序 O(n*log(n)) O(n*log(n)) O(n^2) O(1) 不稳定

TCP/IP

TCP/IP是利用IP进行通信是所必须用到的协议群的统称,包括IP、ICMP、DNS、ARP、TCP、UDP、FTP、HTTP等,他们与TCP、IP关系紧密,故有时也称为TCP/IP网际协议族。其具有两大特点:具有开放性、注重实用性。其标准化的协议,被列入RFC文档并公布。互联网协议=TCP/IP。

TCP/IP分层模型与通信示例

在每个分层中,都会对所发送的数据附加一个首部,TCP包首部、IP包首部、以太网包首部,网络中传输的数据包由两部分组成:协议所要用到的首部、上层传过来的数据。另外,每个分层的包首部汇总还含有一个识别位,用来标示上一层协议的种类信息。

甲给乙发送电子邮件“早上好”

  1. 应用程序处理:进行编码处理(如UTF-8编码),并由应用判断何时发送数据建立TCP连接。
  2. TCP模块的处理:在应用层数据的前端附加一个TCP首部,包含源端口号、目标端口号、序号以及校验和,再发给IP,提供将应用层发来的数据发送至对端的可靠传输。
  3. IP模块的处理:IP将TCP传过来的数据包当做数据,并在TCP首都的前端加上自己的IP首部,包含发送端IP地址和接收端IP地址等。参考路由控制表决定接手此IP包的路由或主机,并发给下一节点的驱动程序。此时要知道接收端的MAC地址,以将MAC地址和IP地址交给以太网的驱动程序,可以利用ARP查找。
  4. 网络接口(以太网驱动)的处理: 给从IP传过来的IP包加上以太网包首部(包含接/发端MAC地址、标志以太网类型的以太网数据的协议)并进行发送处理。发送处理中的FCS由硬件计算,添加到包的最后。
  5. 网络接口(以太网驱动)的处理:主机收到以太网包后,从包首部找到MAC地址,判断是否为发给自己的包,不是则丢弃数据。是的话,检查上层的数据类型,传给相应的子程序,如IP程序。
  6. IP模块的处理:如果是发给自己的IP地址,则可接受数据并查找上一层的协议。在有路由器的情况下,如果不是自己的地址,则借助路由控制表,调查应该送达的主机或路由器后转发数据。
  7. TCP模块的处理:首先计算校验和,判断数据是否被破坏。然后检查是在安装序号接收数据,最后是检查端口号,确定具体的应用程序。接收完毕后发生一个“确认回执”给发送端。
  8. 应用程序的处理:接收端应用程序接收数据,解析数据。给句解析结果反馈信息,如已接受、被退回等。

IP协议

TCP/IP的心脏是互联网层,这一层主要由IP、ICMP、ARP、RARP协议组成。

IP基础

IP大致分为三大作用模块:IP寻址、路由控制以及IP分包和组包。

  • 主机可以自己设置,并具有唯一性,且其不会发生改变。在网桥或交换集线器层转发设备中,不要设置IP地址。主机地址全部为0表示对应的网络地址不可获知,全部为1表示广播地址。
  • 一个数据包之所以能够成功地到达最终的目标地址,全靠路由控制。一跳(Hop)指利用数据连输层以下分层的功能传输数据帧的一起区间。
  • 分片指将较大的IP包分成多个较小的IP包(由于数据链路的最大传输单元MTU的限制)。IP属于面向无连接的数据传输,其可靠性靠上一层的TCP。

IPv4地址

IPv4地址分为四类:ABCD类,开头分别为0 10 110 1110,网络表示分别为8位、16位、24位和32位。D类地址没有主机标示,常被用于多播。另外,主机地址全部为1通常作为广播地址,全部为0表示对应的网络地址或IP地址不可获知的情况才可以用。

子网掩码

  1. IP地址:172.20.100.52 子网掩码:255.255.255.192 (前26位是网络地址)
  2. IP地址:172.20.100.50 /26 (前26位是网络地址,后面6位是主机地址)

IPv4报头

计算机网络的组成

DNS域名服务器(IPv4、IPv6)

DNS为域名服务器,它可以管理所在分层的域的相关信息。根部所设置的DNS叫做根域名服务器,对DNS的检索数据功能起着至关重要的作用。进行DNS查询的主机和软件叫做DNS解析器,用户所使用的工作站或个人电脑都属于解析器。解析器为了调查IP地址,向域名服务器进行查询处理,接收这个查询请求的域名服务器首先会在自己的数据库进行查找,如果有该域名所对应的IP地址就返回,没有就像上一层服务器进行查询处理,知道找到对应的额IP地址。解析器和域名服务器将最新了解到的信息暂时保存在缓存里。DNS不止检索IP地址,还管理众多其他信息,如PTR、NS、A等。

ARP(IPv4、IPv6)

ARP是一种解决地址问题的协议。以目标IP地址为线索,用来定位下一个应该接收数据分包的网络设备对应的MAC地址。ARP借助ARP请求与ARP响应两种类型的包确定MAC地址,源主机要通过广播发送一个ARP请求包,下一个网络设备确定是自己后,将MAC地址塞入ARP响应返回,进而实现IP通信。

  • RARP是ARP反过来,从MAC地址定位IP地址的一种协议。例如通过DHCP自动获取IP地址。
  • 代理ARP:通常ARP包会被路由器隔离,使用代理ARP的路由器可以将ARP请求转发给相邻的网段。

ICMP(IPv4、IPv6)

ICMP的主要功能包括,确认IP包是否成功送达目标地址,通知在发送过程中IP包被废弃的具体原因,改善网络设置等。ICMP的消息大致分为两类:通知出错原因的错误消息、用于诊断的查询消息,主要的ICMP消息有:目标不可达消息、重定向消息、超时消息、返回消息等。ICMP使用IP发送。

DHCP(IPv4、IPv6)

DHCP协议可以实现自动设置IP地址、统一管理IP地址分配,实现即插即用。使用DHCP前,要假设DHCP服务器,并将所要分配的IP地址设置到服务器上,还需要相应的子网掩码、路由控制信息以及DNS服务器的地址等。一般的家庭网络都由宽带路由器冲到DHCP的角色。

IP隧道

IP隧道可以将IPv6网络发过来的包统和为一个数据,再为之追加一个IPv4首部在IPv4网络中传送(要在下个IPv6网络中,去除追加的IPv4首部),也可以将ipv4网络发过来的包统和为一个数据,再为之追加一个IPv6首部在IPv6网络中传送。

TCP与UDP

TCP和UDP是传输层具有代表性的协议。TCP提供可靠的通信传输,而UDP常被用于让广播和细节控制交给应用的不可靠通信传输。传输层要指出具体的程序,使用端口号(有逻辑端口和物理端口,此处指逻辑端口0~65535)这样的一种识别码,通过端口识别,将数据传递给HTTP、FTP等应用层协议。

UDP

UDP是不具有可靠性的数据报协议。它不提供复杂的控制机制,细微的处理它会交给上层的应用去完成,它在收到应用程序发来的数据后,立即鸳鸯发送到网络。UDP主要用于那些对高速传输和实时性有较高要求的通信或广播通信,比如DNS、即时通信等。

TCP

TCP是面向连接的、可靠的流协议,实行顺序控制或重发控制机制,此外还有流控制、拥塞控制、提高网络利用率等众多功能。它只有在确认通信对端存在时才会发送数据,从而可以控制通信流量的浪费。

TCP报头

计算机网络的组成

TCP功能

滑动窗口控制

TCP利用滑动窗口控制提高速度。窗口大小指无须等待确认应答而可以继续发送数据的最大值。利用滑动窗口可以顺序地将多个端同时发送,而不需要等待上一个段的应答,从而提高通信性能。

可靠性(seq ack)

TCP通过肯定的确认应答(ACK)实现可靠的数据传输。在TCP三次握手连接时,主机收到SYN请求,则ACK+1,并返回ACK。在传递数据期间,如果收到的数据的seq等于上次ACK的值,则ACK=seq+len,不等于则返回上次发送的ACK,并返回ACK请求。每次主机收到一个数据或者SYN请求等,都会返回一个ACK数据。ACK的值表示下一个数据的序列号。另外,主机在发送ACK应答时,seq不会加1,但发送SYN请求时,seq会加1。

分段

在建立TCP连接的同时,可以确定发送数据包的单位,称为最大消息长度(MSS:Maximum Segment Size)。最理想的情况时,最大消息长度正好是IP中不会被分片处理的最大数据长度。在三次握手时,两端的主机会在TCP首部的可选项中写入MSS选项,最终的MSS是两个MSS的较小值。

连接管理

  1. 三次握手:主机A向主机B发送SYN请求(TCP数据报,seq=0,ack=0),主机B收到后返回SYN请求&ACK应答(同一个TCP数据报,seq=0,ack=1),主机A收到后返回ACK应答(seq=1,ack=1),则建立连接。在此过程中,同样会携带窗口大小等数据,从而进行流控制。
  2. 发送数据,主机a发送数据包(seq=1,ack=1,上次发送的ack应答并不计数),可以发送多个。主机B每收到一个非ACK数据包就会返回一个ack请求。
  3. A向B发送完数据后,可以发送FIN请求,B向A发送完数据后,也可以发送FIN请求,当双发发送FIN请求并收到ACK应答后,则会切断连接。

窗口控制与重发控制

接收端在收到非自己期望序号的数据时,会将数据保存,并对之前收到的数据进行确认应答。发送端收到三次重复的确认应答后,会进行该数据重新发送。由于可能存在ACK应答丢失情况,发送端收到一个确认应答后,则会判断该应答之前的所有数据都发送成功。

#### 流控制与拥塞控制
接收端主机向发送端主机通知自己可以接收数据的大小(会变换),于是发送端会发送不超过这个限度的数据。TCP首都中有个字段来通知窗口大小。接收端的缓冲区一旦面临数据溢出时,窗口大小的值随之减小并通知发送端,从而进行流量控制。
计算机网络都处在一个共享的环境,在网络出现拥堵时,如果突然发送一个较大量的数据,极有可能导致整个网络的瘫痪。为避免这个问题,通信一开始,就会通过一个慢启动的算法,对发送数据量进行控制。

应用协议

利用网络的应用程序很多,包括web浏览器、电子邮件、远程登录、文件传输、网络管理扥个,能够让这些应用程序进行特定通信处理的正是应用协议。

远程登录

远程登录主要使用TELNET和SSH两种协议,TELNET经常用于登录路由器或高性能交换机等网络设备进行相应的设置。SSH是加密的远程登录系统,可以具有更强的认证机制,可以转发文件,可以使用端口转发功能。OpenSSH是SSH协议的免费开源实现。

WWW万维网

万维网(又称web)是将互联网中的信息以超文本形式展现的系统。WWW定义了3个重要的概念:访问信息的手段和位置(URI)、信息的表现形式(HTML)以及信息转发(HTTP)等。

  • URI(Uniform Resource Identifier)用来标识资源,是一种可以用于WWW之外的高效的识别码,可用于主页地址、电子邮件、电话号码等各种组合中。URL常被用来标示互联网中所有资源的具体位置。
  • HTML:具有纯文本的功能,在页面中可以为文字或图像附加链接。它是WWW通用的数据表现协议,可以认为HTML属于WWW的表示层。另,JavaScript是一种嵌入在HTML中的编程语言。
  • HTTP。当用户在浏览器的地址栏里输入所要访问的Web也的URI后,HTTP的处理机会开始,首先客户端向服务器的80端口建立一个TCP链接,然后在这个TCP连接上进行请求和应答以及数据报文的发送。
  • HTTPS :Web中可以通过TLS/SSL对http通信进行加密,这种http通信叫做HTTPS通信。

计算机网络基础

计算机技术与通信技术的发展和结合,产生了计算机网络,其对计算机系统的组织方式产生了深远的影响。计算机网络最常见的有工业计算机网络(Profibus现场总线、CAN总线和工业以太网等)、上用计算机网络(Internet等)已被广泛地应用于各行各业。可以说,计算机网络是IT和信息产业的基础和核心。

计算机网络简述

从建立一个网络的工程视角来看,建立因特网需要智能终端(PC、服务器、工作站等)、传输介质(光纤、同轴电缆、双绞线、无线电和卫星等)和软件(操作系统、TCP/IP协议、通信软件等)三大部分。

数据交换

数据交换是计算机网络的网络核心。根据原理不同,数据交换可分为电路交换和存储-转发交换。电路交换网络中的复用技术可分为频分复用交换和时分复用交换,存储转发交换可分为分组交换和报文交换。

  • 电路交换的基本思想是:收发双方之间的数据通信过程由三个阶段组成,分别是呼叫阶段(建立连接阶段)、数据传输阶段、释放阶段(断开阶段)。呼叫阶段负责在收发双方之间建立物理通路,包括正向呼叫阶段和方向确认阶段,然后收发双方独占这一物理线路。电路交换的优点是实时性强,管理简单。缺点是手法双方之间独占线路和全部带宽。其适用于实时交互式业务以及大数量传输。为了让更多的用户设备能够同时共用一段线路来发送自己的数据,通常将线路资源按照某种技术划分为“片”,将链路带宽划分为“片”的方法由两种:频分划分和时隙划分。
  • 存储转发交换技术的主要思想是:借鉴了邮政服务的基本思想。数据通信之前,不需要再收发双方之间建立连接,收发双方之间的数据通信以相邻两个节点之间的接力传输完成,只要相邻的两个设备之间的线路是空闲的,一方就可以将自己的数据发送给其邻居节点,下一个节点等到何其下下个节点空闲时,再转发给下下个节点,最终转发给目标节点。报文交换是把需要发送的数据打包成一个文件,分组交换则是把需要发送的数据文件分成多个较小的小文件。其使用与突发性业务、可靠性要求高的业务,如计算机通信。

计算机网络的拓扑结构

常见的拓扑结构有:网状结构、总线结构、环形结构、星形结构、树型结构

网络协议与网络体系结构

不同的设备、介质和语言的计算机网络之间进行通信和数据传输要设计并制定一系列的规则,网络协议则是一组控制数据通信的规则。一个网络协议的基本要素有:语法(指明传输数据的结构格式等)、语义(定义控制信息的具体内容)、同步(定义通信过程的时间先后和速度匹配)。

OSI/RM参考模型

在OSI/RM参考模型中,网络协议体系结构自下而上共分为七层,分别是物理层、数据链路层、网络层、传输层、会话层、表示层和应用层。每个层次都从上层取得数据,加上首部信息形成新的数据单元。

  • 物理层:其任务是实现互联系统间物理介质上位流的透明传输,实现系统间物理通信,其余各层都是虚拟通信。
  • 数据链路层:在两个数据链路层之间建立和维持一条或多条数据链路。它提供无差错(差错校验)的通信服务,为网络层提供透明的帧传输服务。
  • 网络层:接收来自传输层的报文分段,把它们转换成报文分组后送到指定的目的机。
  • 传输层:又称端-端协议。提供一种独立于通信子网的数据传输服务,即对高层隐藏通信子网的结构,使源机和目的机之间的连接就像简单的点对点的连接。
  • 会话层:为两个表示层进程建立会晤连接。
  • 表示层:为应用层提供有关信息表示的服务。
  • 应用层:为用户提供了接口,负责系统中两个应用进程之间的信息交换。

TCP/IP参考模型

在TCP/IP参考模型中,网络协议体系结构自上而下共分为4层,分别是网络接口层、互联网络层、传输层和应用层。

  • Host-to-Network。未做真正描述,仅指出主机必须使用某种协议与网络连接,以便通过网络传递IP分组。
  • Internet层。定义了标准的分组格式和协议(IP协议),控制通信子网提供源点到目的点的IP分组传送(提供不可靠的无连接服务)。
  • Transport层。提供源端到目的端主机上对等实体之间的数据传送服务。TCP和UDP处于此层。
  • Application层。提供各种Internet管理和应用服务功能。

网络协议混合模型

在混合模型中,网络协议体系结构自上而下分为5层,分别是物理层、数据链路层、网络层、传输层和应用层。

  • 物理层。提供透明的比特流传输服务,在信道上传送位流。数据传输方式分为模拟传输(宽度传输)和数字传输(基带传输)。信息交互方式分为单工、半双工、双工。编码与调制:数字数据/模拟数据 -> 数字信号/模拟信号。信道复用技术:频分、时分、波分、码分等。
  • 数据链路层(MAC地址)。提供相邻节点之间的透明帧传输服务,同时也包括差错控制技术等。成帧技术有四种:字符计数法、字符填充法、位填充法和物理层违例码。差错控制技术:奇偶校验技术、海明编码、CRC编码。数据重传和流量控制:停止/等待协议、连续ARQ协议和滑动窗口协议等。
  • 网络层(IP地址)。提供源主机到目的机之间的数据报文传输服务,同时也提供路由选择服务等。因特网中典型的网络层协议有IP、路由协议。网络层必须具备交换、路由和连接管理等三类基本功能。虚电路通信子网(面向连接)和数据报通信子网(面向无连接)。
  • 传输层(端口)。提供源主机进程和目的主机进程之间的数据传输服务。Internet中典型的传输层协议有TCP和UDP。TCP使用三次握手建立连接。
  • 应用层。支持网络应用,接收来自应用程序的进程并未应用程序提供数据传输服务。Internet中常见的应用层协议有FTP、SMTP、HTTP等。DNS是运行在UDP协议上的域名解析系统。

物理层、链路层

物理层

采取不同的传输工作方式(单工、半双工、全双工),将相应的01数据(数字/模拟数据),进行加工转换(调制、编码)为在不同传输介质(双绞线、光纤等)传输的不同格式(高低电平、曼彻斯特、块编码)的信号(数字/模拟信号)。一个脉冲称为一个码元,由于传输的物理特性等限制,有最大传输速率限制(波特率:奈归斯特、比特率:香农)以及通道共享方案(频分、时分等)。

  1. 数字数据到数字信号的编码技术有:不归零编码技术(NRZ-L和NRZ-I反相)、曼彻斯特编码技术(每位中间有电平跳变、二义性)、差分曼彻斯特编码技术以及以太网中采用的4B/5B、8B/10B块编码技术(用NRZ-I编码方式传输,不多于3个连续的0)等。
  2. 奈茥斯特定律:理想的、频带宽度为W的低通信道,最高码元传输速率-波特率是2W。同样的带通信道,最高波特率为W。波特率:信号/码元每秒钟变化次数。
  3. 香农公式:极限比特率为C=Wlog2(1+S/N)。S/N表示信噪比,S信道内信号的平均功率,N是信道内部的高斯噪声功率。比特率:每秒钟传递bit位个数

数据链路层

通过调用物理层服务,再结合差错控制(奇偶校验、海明码、CRC编码)、数据重传&流量控制(发送应答、连续ARQ、ARQ选择重传等滑动窗口协议)等在网络节点间实现可靠的帧传输服务。另外还需要考虑链路控制方案ALOHA等。

  1. 成帧的基本技术有:字符计数成帧技术(计数首部+数据)、字符填充成帧技术(帧头DLE STX+数据+DLE ETX)、位填充成帧技术(帧头01111110+数据+01111110)、物理层违例码成帧技术等。
  2. 以太网常采用Ethernet II帧格式:前导码(8byte)+目的地址(6)+源地址(6)+类型(2)+数据+FCS(4)。其能传递的最大帧是1518,减去以太网帧头(14)和帧尾(4),故最大传输单元MTU为1500字节(为什么没有前导码?希望有朋友可以指出)。
  3. 传输速率又称带宽,表示两个设备间数据流动的物理速度,单位为bps(Bits Per Second)。主机之间实际的传输速率被称为吞吐量(单位也是bps),与带宽、主机CPU处理能力、网络拥堵程度、报文数据字段比例等有关。

网络的构成要素

计算机网络的组成

通信媒介与数据链路

计算机之间通过电缆相互连接。电缆分为很多种,包括双绞线电缆、光纤电缆、同轴电缆、串行电缆等。不同的数据链路有不同的媒介、传输速率和用途等。例如,以太网的通信媒介有同轴电缆、双绞线电缆、光纤电缆。

网卡NIC

任何一台计算机连接网络时,都需要使用网卡(网络接口卡),又叫网络适配器、网卡、LAN卡。笔记本一般都有内置NIC。

中继器

中继器是在物理层面上延长网络的设备,由电缆传过来的电信号或者光信号通过中继器进行波形调整和放大,再传到另一个电缆。一般情况下,中继器两端的通信介质是相同的。有些中继器可以提供多个端口服务,这种中继器称为中继集线器或集线器。
通过中继器而进行的网络延长,其距离有限制。比如一个10Mbps的以太网最多可以用4个中继器分段连接,而一个100Mbps的以太网则最多只能连两个中继器。

网桥/2层交换机

网桥是在链路层层面上连接两个网络的设备。它能够识别数据链路层中的数据帧,并将这些数据帧临时存储于内存,再重新生成信号作为一个全新的帧转发给相邻的另一个网段。网桥可以校验数据是否正确送达目的地,并能通过地址(MAC地址)自学机制和过滤功能控制网络流量。以太网等网络中经常使用的交换集线器(Hub),现在基本也属于网桥的一种。

路由器/3层交换机

路由器是在网络层层面上连接两个网络、并对分组报文进行转发的设备。路由器是根据IP地址进行处理的。路由器可以连接两个不同的数据链路,现在人们在家或实验室连接互联网时使用的宽度路由器也是路由器的一种。路由器还有分担网络负荷的作用(隔绝链路层的广播消息等),有些路由器还具备一定的网络安全功能。

4~7层交换机

4~7层交换机负责处理从传输层到应用层的数据。它以TCP等协议的传输层以及上面的应用层为基础,分析收发数据,并对其进行特定的处理。如,企业通常假设多台服务器(同一URL)来负担前端的访问需求,这些服务器的前端加的负载均衡器就是其一。以及,实际通信是,在网络拥堵时,优先处理语音等及时性要求高的通信请求的宽度控制也是4~7层交换机的重要功能。其他如广域网加速器、特殊应用访问加速以及防火墙(防止互联网的非法访问)等。

网关

网关是OSI参考模型中负责将从运输层到应用层的数据进行转换和转发的设备。网关与4~7层交换机的区别是网关还负责对数据进行转换。如互联网邮件和手机邮件之间的转换服务。以及,在万维网中,为了控制网络流量以及处于安全,使用的代理服务器也属于网关的一种——应用网关。

网络安全

防火墙

防火墙的种类和形态有很多种,如专门过滤特定数据包的包过滤防火墙、数据到达应用后由应用处理并拒绝非法访问的应用网关等,其基本设计思路为:暴露给危险的主机和路由器的个数要有限。比如,设置防火墙,可以限制从互联网访问的主机个数,限制只能内网访问,限制端口的访问等。

IDS(入侵检测系统)

数据包符合安全策略,防火墙会让其通过,但无法判断当前访问是否为非法访问,而IDS正是检查这种非法访问的情况,并及时通知网络管理员的系统。一般在防火墙或DMZ等便捷设备上进行设置。IDS有定期采集日志、长期监控、通知异常等功能。

反病毒/个人防火墙

反病毒和个人防火墙是继IDS和防火墙之后的另外两种安全对策,是用户使用的软件。

加密技术基础

为了防止信息的泄漏、实现机密数据的传输,出现了各种各样的加密技术(出现在各层)。如PKI、CA数字证书等。

  • 加密是利用某个值(密匙)对明文的数据通过一定的算法变换成加密数据的过程,逆反过程称为解密。
  • 身份认证技术。在实时安全对策时,有必要验证使用者的正确性和真实性,要用到认证技术。

大学计算机基础

计算与计算思维

“计算”这个词从狭义来说,是根据已知量算出未知量,从广义上说,是一个可以领会却难以言表的概念,可以理解为考虑或谋虑,该怎么办。电子数字计算机的出现和计算机科学的发展泛化了这个概念。计算是人类基本思维活动和行为方式的主要方面之一,也是人们认识世界和改造世界的基本方法,主要是用数学和逻辑的方法来决定事情的处理过程。

计算思维

计算思维是运用计算机科学基础概念进行问题求解、系统设计以及人类行为理解等涵盖计算机科学之广度的一系列思维活动。计算思维代表着一种普遍的态度和一类普适的能力,目前大家认可的计算思维有以下特征:

  • 计算思维是概念化的抽象思维,不只是程序设计,还要求对事物能够在抽象的多个层次上思维。
  • 计算思维是基本的,而不是刻板的技能。
  • 计算思维是人的,而不是计算机的思维方式。
  • 计算思维是数学和工程思维的互补和融合。
  • 计算思维是思想,而不是人造物。
  • 计算思维面向所有人,所有的地方。
  • 计算思维关注依旧亟待理解和解决的智力上极有挑战性并且引人入胜的科学问题。

科技创新三大思维

科学界一般认为,科学方法分为理论、实验和计算三大类,相对应的是三大科学思维:理论思维、实验思维和计算思维

  • 理论思维以数学为基础。公理化方法是最重要的理论思维方法。公理化系统有三个条件:无矛盾性、独立性、完备性。
  • 实验思维以物理等学科为基础。对实验思维来说,最为重要的事情就是设计、制造实验仪器和追求理想的实验环境。
  • 计算思维以计算机科学为基础。数学和工程思维的互补和融合很好的体现在抽象、理论和设计3个形态/过程上。

可计算性和算法

可计算性是指一个实际问题是否可以使用计算机来解决。可计算性理论是研究计算的一般性质的数学理论,也称为算法理论。计算的过程就是执行算法的过程。可计算函数的精确定义是:能够在抽象计算机上编出程序并计算其值的函数。图灵机就是一种在理论计算机科学中广泛采用的抽象计算机,可用一个图灵机来计算其值的函数是可计算函数,找不到图灵机来计算其值的函数是不可计算函数。建立计算的数学模型是可计算性理论的中心问题。在可计算性理论中,将问题分为可计算的和不可计算的。在复杂性理论中,目标是把可计算的问题分成简单的和困难的,研究的是算法的时间复杂性和空间复杂性,主要解决算法的效率思维。

图灵和图灵机

所谓的图灵机就是指一个抽象的机器,它有一条无限长的纸带,纸带分成了一个一个的小方格,每个方格有不同的颜色。有一个机器头在纸带上移来移去。机器头有一组内部状态,还有一些固定的程序。在每个时刻,机器头都要从当前纸带上读入一个方格信息,然后结合自己的内部状态查找程序表,根据程序输出信息到纸带方格上,并转换自己的内部状态,然后进行移动。
图灵机
图灵机的基本思想是用机器来模拟人用纸笔进行数字运算的过程,可用图灵机来计算其值的函数称为可计算函数。可以证明,存在一个通用通用图灵机,它可以模拟任何其他的图灵机,通用图灵机正是后来出现的存储指令的通用数字计算机的理论原型。半个多世纪以来,数学家提出的各种各样的计算模型都被证明是和图灵机等价的。

算法

算法可以理解为由基本运算及规定的运算顺序所构成的完整的解题步骤。或看成按照要求设计好的有限的确切的计算序列,并且他可以解决一类问题。算法不等于程序,不等于计算方法,程序的编制不可能优于算法的设计。

算法的特征有:可行性、确定性、有穷性、输入、输出。描述算法的工具有自然语言、传统流程图、PAD图、N-S图和伪代码等。

算法的基本要素为:

  • 对数据对象的运算和操作。基本的运算和操作有四类:算术运算、逻辑运算(与或非)、关系运算(大小是否相等)、数据传输(赋值、输入、输出等)
  • 算法的控制结构。算法中各操作之间的执行顺序称为算法的控制结构,基本的控制饥饿哦股有:顺序、选择、循环。

算法设计的基本方法:列举法、归纳法、递推、递归、回溯法。

算法的复杂度分为:1. 空间复杂度,是对算法所需存储空间的度量。2. 时间复杂度,指执行算法所需要的计算工作量。通常一个算法所用时间等于编译时间加上运行时间。

问题求解的基本步骤

计算机学科为计算机有关问题的求解提供了基本的框架,一般问题求解可以归纳为4个主要步骤:

  1. 理解问题。即弄清问题的意思,以及问题中设计的属于、词汇的含义,分清问题中的条件和结论等。
  2. 制定计划。在理解问题的基础上,运用有关的数学模型和方法拟定出解决问题的思路和方法。
  3. 执行计划。执行计划,检查每个执行步骤,保持执行过程的准确记录。
  4. 反思展望。对整个解题过程进行必要的检查和反思,也包括检验得到的答案是否适合和符合问题的实际。

计算机概述

计算机发展

计算机的发展经历了大型计算机、微型计算机和计算机网络等不同阶段。在计算机不同的发展阶段,其决定性作用的是电子元器件。所以,计算机发展阶段通常按照计算机中主要功能部件所采用的电子器件(逻辑原件)的不同来划分。一般讲计算机发展分为4个阶段,习惯上称为4代:电子管计算机、晶体管计算机、集成电路计算机和大规模/超大规模集成电路计算机。
第四代计算机的另一个重要分支是以大规模、超大规模集成电路为基础发展起来的微处理器(CPU)和微型计算机。未来计算机的芯片的制造技术可能为:超导技术、纳米技术、光技术、生物技术和量子技术。

计算机分类

目前,国内外计算机界以及各类教科书都是采用国际沿用的分类方法,一般把计算机分为巨型机、大型主机、小型机(8~12颗CPU)、工作站(以个人计算机和分布式网络计算为基础,主要面向专业应用领域而设计开发的高性能计算机)和个人计算机等几种类型。

计算机特点及发展趋势

计算机是一种可以进行自动控制、具有记忆功能的现代化计算工具和信息处理工具。它有以下5个方面的优点:1.运算速度快 2.计算精度高 3.记忆能力强 4.具有逻辑判断能力 5.可靠性高,通用性强。

计算机的发展表现为:巨型化(速度、存储量等方面)、微型化、多媒体(交互方式)、网络化和智能化。

计算机的主要用途为:数值计算、数据及事务处理、自动控制与人工智能、通信与网络、电子商务、物联网、云计算。

计算机基础知识

计算机系统组成

一个完整的计算机系统是由硬件系统和软件系统组成的。
计算机硬件系统由运算器、控制器、存储器、输入设备和输出设备组成。控制器控制存储器、运算器、输入输出设备。数据从输入设备传给存储器,经由运算器计算后再返回给存储器,最后在输出设备上显示。存储器会传递数据给控制器。
计算机软件系统层次有:裸机、操作系统、开发工具(支撑软件)、应用软件。

计算机工作原理

计算机的工作原理,其主要特点是:

  • 计算机硬件系统由运算器等五大部件主城,并规定了他们的基本功能
  • 计算机内部采用二进制来表示指令和数据。每一条指令通常包括操作码和地址码。
  • 使用单一的处理部件来完成计算、存储以及通讯的工作。
  • 存储单位是定长的线性组织。存储空间的单元是直接寻址的。
  • 在执行程序和处理数据时,必须将程序和数据从外存储器装入内存储器中,然后才能使计算机在工作时自动地从存储器中取出指令并加以执行。

计算机编码系统

计算机中不但使用数值型数据(二/八/十/十六进制等),还大量使用非数值型数据,如字符、汉字等。信息编码就是指对数据计算机的各种数值和非数值型数据用二进制进行编码的方式。在输入过程中,系统自动将用户输入的各种数据按编码的类型转换成相应的二进制形式存入计算机存储单元中。在输出过程中,再由系统自动地将二进制编码数据转换成用户可以识别的数据格式输出给用户。常用的编码方式有

  • BCD编码,即二-十进制编码。用四位二进制表示十进制数,四位分别表示8/4/2/1.
  • ASCII码。一个ASCII码占用一个字节(最高位为0),来表示十进制、大小写英文字母、常用的运算符和标点符号等共128个。
  • 汉字编码。根据一字一码的原则,国际码(GB 2312-80)字符规定,每个字符有一个2字节代码(区码/位码)组成,每个字节的最高位为0。汉字通过输入设备将外码送入计算机,再由汉字系统将其转换为内码(GB内码,两个字节其高位都为1)存储、传送和处理,当需要输出时,再由汉字系统调用字库(点阵)中汉字的字形码得到结果并输出。

微型计算机硬件

微型计算机,简称“微型机”或“微机”,是发展最快的一类计算机。下图为微型计算机组成图:
微型计算机系统组成

主板

主板是一个插槽的几何体,也是整个硬件系统的平台,微机的各个部件都要直接插在主板上或者通过电缆连接在主板上。它主要有两个功能:提供CPU、内存和各种功能卡的插座,以及,为各种常用外部设备提供通用接口。主板主要部件有:芯片组、CPU插座、内存插糟、总线扩展槽、输入/输出接口、基本输入输出系统BIOS和CMOS。

微机总线

总线是各部件见有效高速传输各种信息的通道。总线一般分为内部总线、系统总线和外部总线。

  • 内部总线。即微处理器级总线,包括地址总线、数据综合和控制总线,从CPU引脚引出,用来实现CPU与外围控制芯片(主存、Cache等)。常见的总线有:I2C总线、SPI总线、SCI总线。
  • 数据总线。又称为I/O通道总线,同样包括地址线、数据线和控制线,用于CPU和接口卡的连接。常见的总线标准有:ISA总线、PCI总线、AGP总线等。
  • 外部总线。是微机和外部设备之间的总线,常见的总线有:RS-232C总线、USB总线、RS.485总线和IEEE-488总线等。

微处理器

微机的CPU一般由运算器、控制器和寄存器三个部分组成,通过CPU内部总线连接在一起。其性能主要包括:主频(执行指令的速度)、字长(一次处理的二进制位数)、几核等。

内存储器

内存储器分为只读存储器(ROM)、随机读/写存储器和高速缓冲存储器三类。

  • 只读存储器(Read Only Memory)。ROM所存数据稳定,断电后所存数据也不会改变,结构简单,因此常用用于存储各种固定程序和数组。ROM在没有通电时也能将数据记录下来,是一种非挥发性内存。
  • 随机读/写存储器(Random Access Memory)。RAM是计算机工作的存储区,一起要执行的程序和数据都要先装入该存储器内。存储器的数据可以反复使用,断电后,数据会消失。
  • 高速缓冲存储器(Cache)。是CPU与内存之间设置的一级或两级高速校容量存储器。

其他

  • 硬盘的存储量较大,其主要性能技术指标有:容量、转速、平常寻道时间等,常见的借口方式有:IDE接口、SATA接口、SCSI借口、SAS接口、光纤通道和USB接口等。
  • 声卡。声卡是处理声音的设备,它具有把声音编程相应数字信号,以及再将数字信号转换成声音的A/D、D/A转换功能。
  • 显卡又称显示适配器,是计算机最基本、最重要的配件之一。显卡是电脑进行数模信号转换的设备,承担输出显示图形的任务,具有图像处理能力,可协助CPU工作,提高整体的运行速度。
  • 常见输入设备:鼠标、键盘、扫描仪等。
  • 常见输出设备: 显示器、打印机、音箱等。