转自:http://java.ccidnet.com/art/12015/20080603/1466033_1.html
1、创建高级对象
使用构造函数来创建对象
构造函数是一个函数,调用它来例示并初始化特殊类型的对象。可以使用 new 关键字来调用一个构造函数。下面给出了使用构造函数的新示例。
var myObject = new Object(); // 创建没有属性的通用对象。
var myBirthday = new Date(1961, 5, 10); // 创建一个 Date 对象。
var myCar = new Car(); // 创建一个用户定义的对象,并初始化其属性。
通过构造函数将一个参数作为特定的 this 关键字的值传递给新创建的空对象。然后构造函数负责为新对象执行适应的初始化(创建属性并给出其初始值)。完成后,构造函数返回它所构造的对象的一个参数。
编写构造函数
可以使用 new 运算符结合像 Object()、Date() 和 Function() 这样的预定义的构造函数来创建对象并对其初始化。面向对象的编程其强有力的特征是定义自定义构造函数以创建脚本中使用的自定义对象的能力。创建了自定义的构造函数,这样就可以创建具有已定义属性的对象。下面是自定义函数的示例(注意 this 关键字的使用)。
function Circle (xPoint, yPoint, radius) {
this.x = xPoint; // 圆心的 x 坐标。
this.y = yPoint; // 圆心的 y 坐标。
this.r = radius; // 圆的半径。 }
调用 Circle 构造函数时,给出圆心点的值和圆的半径(所有这些元素是完全定义一个独特的圆对象所必需的)。结束时 Circle 对象包含三个属性。下面是如何例示 Circle 对象。
var aCircle = new Circle(5, 11, 99);
使用原型来创建对象
在编写构造函数时,可以使用原型对象(它本身是所有构造函数的一个属性)的属性来创建继承属性和共享方法。原型属性和方法将按引用复制给类中的每个对象,因此它们都具有相同的值。可以在一个对象中 更改原型属性的值,新的值将覆盖默认值,但仅在该实例中有效。属于这个类的其他对象不受此更改的影响。
下面给出了使用自定义构造函数的示例,Circle(注意 this 关键字的使用)。
Circle.prototype.pi = Math.PI;
function ACirclesArea () { return this.pi * this.r * this.r;
// 计算圆面积的公式为 ?r2。 } Circle.prototype.area = ACirclesArea;
// 计算圆面积的函数现在是 Circle Prototype 对象的一个方法。
var a = ACircle.area();
// 此为如何在 Circle 对象上调用面积函数。
使用这个原则,可以给预定义的构造函数(都具有原型对象)定义附加属性。
例如,如果想要能够删除字符串的前后空格(与 VBScript 的 Trim 函数类似),就可以给 String 原型对象创建自己的方法。
// 增加一个名为 trim 的函数作为
// String 构造函数的原型对象的一个方法。
String.prototype.trim = function() {
// 用正则表达式将前后空格
// 用空字符串替代。
return this.replace(/(^\s*)|(\s*$)/g, ""); }
// 有空格的字符串 var s = " leading and trailing spaces ";
// 显示 " leading and trailing spaces (35)" window.alert(s + " (" + s.length + ")");
// 删除前后空格 s = s.trim();
// 显示"leading and trailing spaces (27)"
window.alert(s + " (" + s.length + ")");
2.递归
递归是一种重要的编程技术。该方法用于让一个函数从其内部调用其自身。一个示例就是计算阶乘。0 的阶乘被特别地定义为 1。
更大数的阶乘是通过计算 1 * 2 * ...来求得的,每次增加 1,直至达到要计算其阶乘的那个数。
下面的段落是用文字定义的计算阶乘的一个函数。
“如果这个数小于零,则拒绝接收。如果不是一个整数,则将其向下舍入为相邻的整数。如果这个数为 0,则其阶乘为 1。如果这个数大于 0,则将其与相邻较小的数的阶乘相乘。”
要计算任何大于 0 的数的阶乘,至少需要计算一个其他数的阶乘。用来实现这个功能的函数就是已经位于其中的函数;该函数在执行当前的这个数之前,必须调用它本身来计算相邻的较小数的阶乘。这就是一个递归示例。
递归和迭代(循环)是密切相关的 ? 能用递归处理的算法也都可以采用迭代,反之亦然。确定的算法通常可以用几种方法实现,您只需选择最自然贴切的方法,或者您觉得用起来最轻松的一种即可。
显然,这样有可能会出现问题。可以很容易地创建一个递归函数,但该函数不能得到一个确定的结果,并且不能达到一个终点。这样的递归将导致计算机执行一个“无限”循环。下面就是一个示例:在计算阶乘的文字描述中遗漏了第一条规则(对负数的处理) ,并试图计算任何负数的阶乘。这将导致失败,因为按顺序计算 -24 的阶乘时,首先不得不计算 -25 的阶乘;然而这样又不得不计算 -26 的阶乘;如此继续。很明显,这样永远也不会到达一个终止点。
因此在设计递归函数时应特别仔细。如果怀疑其中存在着无限递归的可能,则可以让该函数记录它调用自身的次数。如果该函数调用自身的次数太多,即使您已决定了它应调用多少次,就自动退出。
下面仍然是阶乘函数,这次是用 JScript 代码编写的。
// 计算阶乘的函数。如果传递了// 无效的数值(例如小于零),
// 将返回 -1,表明发生了错误。若数值有效,
// 把数值转换为最相近的整数,并// 返回阶乘。
function factorial(aNumber) {
aNumber = Math.floor(aNumber); // 如果这个数不是一个整数,则向下舍入。
if (aNumber < 0) {// 如果这个数小于 0,拒绝接收。
return -1;
}
if (aNumber == 0) { // 如果为 0,则其阶乘为 1。
return 1;
}else return (aNumber * factorial(aNumber - 1)); // 否则,递归直至完成。
}
3.变量范围
JScript 有两种变量范围:全局和局部。如果在任何函数定义之外声明了一个变量,则该变量为全局变量,且该变量的值在整个持续范围内都可以访问和修改。如果在函数定义内声明了一个变量,则该变量为局部变量。每次执行该函数时都会创建和破坏该变量;且它不能被该函数外的任何事物访问。
像C++这样的语言也有“块范围”。在这里,任何一对“{}”都定义新的范围。JScript 不支持块范围。
一个局部变量的名称可以与某个全局变量的名称相同,但这是完全不同和独立的两个变量。因此,更改一个变量的值不会影响另一个变量的值。在声明局部变量的函数内,只有该局部变量有意义。
var aCentaur = "a horse with rider,"; // aCentaur 的全局定义。
// JScript 代码,为简洁起见有省略。
function antiquities() // 在这个函数中声明了一个局部 aCentaur 变量。
{ // JScript 代码,为简洁起见有省略。
var aCentaur = "A centaur is probably a mounted Scythian warrior";
// JScript 代码,为简洁起见有省略。
aCentaur += ", misreported; that is, "; // 添加到局部变量。
// JScript 代码,为简洁起见有省略。 }
// 函数结束。 var nothinginparticular = antiquities();
aCentaur += " as seen from a distance by a naive innocent.";
/* 在函数内,该变量的值为 "A centaur is probably a mounted Scythian warrior, misreported; that is, ";在函数外,该变量的值为这句话的其余部分:
"a horse with rider, as seen from a distance by a naive innocent." */ 很重要的一点是注意变量是否是在其所属范围的开始处声明的。有时这会导致意想不到的情况。 tweak(); var aNumber = 100;
function tweak() {
var newThing = 0; // 显式声明 newThing 变量。
// 本语句将未定义的变量赋给 newThing,因为已有名为 aNumber 的局部变量。
newThing = aNumber;
//下一条语句将值 42 赋给局部的 aNumber。aNumber = 42;
if (false) {
var aNumber; // 该语句永远不会执行。
aNumber = 123; // 该语句永远不会执行。
} // 条件语句结束。
} // 该函数定义结束。
当 JScript 运行函数时,首先查找所有的变量声明,var someVariable;并以未定义的初始值创建变量。如果变量被声明时有值,var someVariable = "something";那么该变量仍以未定义的值初始化,并且只有在运行了声明行时才被声明值取代,假如曾经被声明过。
JScript 在运行代码前处理变量声明,所以声明是位于一个条件块中还是其他某些结构中无关紧要。JScript 找到所有的变量后立即运行函数中的代码。如果变量是在函数中显式声明的?也就是说,如果它出现于赋值表达式的左边但没有用 var 声明 ? 那么将把它创建为全局变量。复制、传递和比较数据 在 JScript 中,对数据的处理取决于该数据的类型。
按值和按引用的比较
Numbers 和 Boolean 类型的值 (true 和 false) 是按值来复制、传递和比较的。当按值复制或传递时,将在计算机内存中分配一块空间并将原值复制到其中。然后,即使更改原来的值,也不会影响所复制的值(反过来也一样),因为这两个值是独立的实体。对象、数组以及函数是按引用来复制、传递和比较的。 当按地址复制或传递时,实际是创建一个指向原始项的指针,然后就像拷贝一样来使用该指针。如果随后更改原始项,则将同时更改原始项和复制项(反过来也一样)。实际上只有一个实体;“复本”并不是一个真正的复本,而只是该数据的又一个引用。当按引用比较时,要想比较成功,两个变量必须参照完全相同的实体。例如,两个不同的 Array 对象即使包含相同的元素也将比较为不相等。要想比较成功,其中一个变量必须为另一个的参考。要想检查两个数组是否包含了相同的元素,比较 toString() 方法的结果。 最后,字符串是按引用复制和传递的,但是是按值来比较的。请注意,假如有两个 String 对象(用 new String("something") 创建的),按引用比较它们,但是,如果其中一个或者两者都是字符串值的话,按值比较它们。注意 鉴于 ASCII和 ANSI 字符集的构造方法,按序列顺序大写字母位于小写字母的前面。例如 "Zoo" 小于 "aardvark"。如果想执行不区分大小写的匹配,可以对两个字符串调用 toUpperCase() 或 toLowerCase()。传递参数给函数 按值传递一个参数给函数就是制作该参数的一个独立复本,即一个只存在于该函数内的复本。即使按引用传递对象和数组时,如果直接在函数中用新值覆盖原先的值,在函数外并不反映新值。只有在对象的属性或者数组的元素改变时,在函数外才可以看出。
例如(使用 IE 对象模式):
// 本代码段破坏(覆盖)其参数,所以
// 调用代码中反映不出变化。
function Clobber(param) {
// 破坏参数;在调用代码中
// 看不到。
param = new Object();
param.message = "This will not work"; }
// 本段代码改变参数的属性,
// 在调用代码中可看到属性改变。
function Update(param) {
// 改变对象的属性;
// 可从调用代码中看到改变。
param.message = "I was changed"; }
// 创建一个对象,并赋给一个属性。
var obj = new Object();
obj.message = "This is the original";
// 调用 Clobber,并输出 obj.message。注意,它没有发生变化。
Clobber(obj);
window.alert(obj.message); // 仍然显示 "This is the original"。
// 调用 Update,并输出 obj.message。注意,它已经被改变了。
Update(obj);
window.alert(obj.message); // 显示 "I was changed"。
检验数据
当按值进行检验时,是比较两个截然不同的项以查看它们是否相等。通常,该比较是逐字节进行的。当按引用进行检验时,是看这两项是否是指向同一个原始项的指针。如果是,则比较结果是相等;如果不是,即使它们每个字节都包含完全一样的值,比较结果也为不相等。
按引用复制和传递字符串能节约内存;但是由于在字符串被创建后不能进行更改,因此可以按值进行比较。这样可以检查两个字符串是否包含相同的内容,即使它们是完全独立产生的。
分享到:
相关推荐
"JavaScript高级代码例子"这个主题涵盖了JavaScript的高级特性和实践应用,旨在帮助开发者深入理解和运用这些高级技术。以下是对这些高级知识点的详细阐述: 1. **闭包(Closures)**:闭包是JavaScript中的一个...
5. 调试和测试:为了保证代码质量,JavaScript的调试和测试也是高级应用中不可或缺的一部分。文档可能会讲解如何使用开发者工具进行代码调试、性能分析以及单元测试和集成测试的策略。 6. 最新ES规范特性:...
通过阅读《JavaScript高级程序设计(第3版)》,开发者不仅可以掌握JavaScript的基本用法,还能深入理解其内部机制,从而编写出更高效、更易于维护的代码。这本书对于想要提升JavaScript技能的前端开发者或全栈...
李炎恢在线课堂的JavaScript讲义和课程代码旨在深入浅出地教授这一重要技能,帮助学习者掌握JavaScript的基本概念、语法以及实际应用。 JavaScript的核心特性包括变量、数据类型、控制流(条件语句和循环)、函数、...
"JavaScript高级编程"这本书深入探讨了这门语言的高级特性和最佳实践,旨在帮助开发者提升技能水平,实现更高效、更可靠的代码编写。以下是该书可能涵盖的一些关键知识点: 1. **基础语法**:包括变量、数据类型...
总的来说,这个压缩包文件提供了一个学习和研究JavaScript实际应用的平台,涵盖了JavaScript的各个方面,无论是基础语法还是高级特性的运用,都能在其中找到示例。通过深入理解和实践这些代码,开发者可以提升自己的...
Rhino是Mozilla基金会开发的一个开源的JavaScript引擎,它可以嵌入到Java应用程序中,使得Java应用能够执行JavaScript代码。 描述中提到的文章链接已经失效,但根据上下文,我们可以推测文章提供了如何使用...
总的来说,《Head First JavaScript源码》涵盖了JavaScript的各个方面,从基础语法到高级特性,再到实际应用。通过阅读源码,读者不仅可以学习到理论知识,还能看到这些知识如何在实践中得以体现,这对于初学者深入...
JavaScript代码压缩工具是一种优化网页性能的关键技术,尤其在当今互联网应用越来越复杂,JavaScript文件体积日益庞大的背景下,其重要性不言而喻。压缩JavaScript代码的主要目的是减少文件大小,提高网络传输效率,...
"超全的javascript应用小程序"这个主题涵盖了JavaScript在开发小型应用程序和功能时的各种技巧和方法,旨在帮助开发者提高效率和代码质量。 1. **原生JavaScript技巧**:原生JavaScript意味着不依赖任何库或框架,...
本资源“Javascript开发技术大全源代码”提供了一个全面的JavaScript学习和实践平台,涵盖了从基础到高级的各种技术。 在JavaScript的世界里,了解基本语法是至关重要的。这包括变量、数据类型(如字符串、数字、...
了解这些基础知识是编写JavaScript代码的前提。 2. **对象**:JavaScript中的对象是一种复杂的数据结构,允许我们存储和操作键值对。通过字面量语法或构造函数可以创建对象。理解原型链、对象的继承机制以及如何...
此压缩包“JavaScript应用程序经典实例全书源码”很可能包含了各种JavaScript编程的经典案例,这些实例可以帮助我们深入理解和掌握JavaScript的核心概念和技术。 在JavaScript的世界里,有几个重要的知识点是每个...
"JavaScript高级程序设计"是一本深入探讨JavaScript编程语言的书籍,旨在帮助读者掌握JS的各个方面,适合自学者进行系统...通过学习这些内容,读者可以全面掌握JavaScript,从而能够编写出高效、健壮的Web应用程序。
3. C#:微软的面向对象的编程语言,有时与JavaScript结合,如通过TypeScript为JavaScript提供静态类型支持,或在Blazor框架中编写服务器端代码。 4. Java:另一种广泛应用的编程语言,尤其在服务器端开发中。...
7. **性能优化**:包括DOM操作优化、事件处理优化、内存管理、代码执行效率提升等,这些都是高级JavaScript开发者必须关注的话题。 8. **错误处理**:学会有效地捕获和处理错误,是保证程序稳定运行的关键。理解try...
这些内容有助于编写更高效、更简洁的代码。同时,ES6及以后的新特性,如解构赋值、模板字符串、Set和Map等,也会被详细讲解,使学习者能够跟上语言的发展步伐。 在实际应用中,JavaScript常常与AJAX、WebSocket等...
以上就是JavaScript在广告实例中的主要应用,从基础到高级,涵盖了多种广告形式和技术。通过学习和实践这些代码,开发者可以提升自己的技能,为网站创建更高效、更具吸引力的广告体验。在实际项目中,还需要关注性能...
以上知识点涵盖了JavaScript的基础到高级应用,"超实用的javascript代码段"这本书籍的源码将通过实例展示这些概念,为读者提供实践和学习的机会。通过阅读和分析这些代码,可以加深对JavaScript的理解,提升编程能力...
通过研究这些源代码,你可以深入了解DOM API的使用,提高编写高效、可维护的JavaScript代码的能力。同时,将理论知识与实践相结合,有助于培养解决实际问题的技能。记得在阅读和学习过程中,不仅要理解代码的功能,...