JavaScript 面向对象(三) —— 高级篇 JavaScript 面向对象(一) —— 基础篇JavaScript 面向对象(二) —— 案例篇

前端之家收集整理的这篇文章主要介绍了JavaScript 面向对象(三) —— 高级篇 JavaScript 面向对象(一) —— 基础篇JavaScript 面向对象(二) —— 案例篇前端之家小编觉得挺不错的,现在分享给大家,也给大家做个参考。

JavaScript 面向对象(一) —— 基础篇

JavaScript 面向对象(二) —— 案例篇

 

一、json方式的面向对象

首先要知道,js中出现的东西都能够放到json中。关于json数据格式这里推荐一篇博客JSON 数据格式

先看下json创建的简单对象:相比基础篇中的构造函数、原型等的创建方式,json方式简单方便;但是缺点很明显,如果想创建多个对象,那么会产生大量重复代码,不可取。

JSON方式适用于只创建一个对象的情况,代码简介又优雅。

 1 <!DOCTYPE html>
 2 <html 3     head 4         Meta charset="UTF-8" 5         title></ 6         script 7             var person = {
 8                 name: "jiangzhou, 9                 age: 2210                 showName: function(){
11                     alert(this); //[Object Object]
12 姓名:+.name);
13                 },1)">14                 showAge: 15 年龄:.age);
16                 }
17             };
18             person.showName();
19             person.showAge();
20             
21         </22     23 >

JSON在JS面向对象的应用中,主要的一个作用就是命名空间:如果有大量常用的js函数,利用json,我们可以将同一类函数放在一个“类”里,类似于java那样,这样我们就能很好的管理和查找使用这些js函数,看下面的例子就很好理解了。

仿java.lang包
 8              lang  {};
 9             
10             /**
             * 仿java.lang.Math类
12              */
            lang.Math 14                                  * 求绝对值
                 * @param {Object} a
17                                  abs: (a){
19                     return a > 0 ? a : -a;
20 21                 22                  * 求最大值
23 24                  * @param {Object} b
25                  26                 max: (a,b){
27                     > b  a : b;
28 29                 30                  * PI
31                  32                 PI: 3.1415926
33             }
34             
35             36              * 仿java.lang.String类
37              38             lang.String 39                 40                  * 求字符串长度
41                  * @param {Object} str
42                  43                 length: (str){
44                      str.length;
45 46                 47                  * 将字符串转为小写
48 49                  50                 toLowerCase: 51                      str.toLowerCase();
52 53                 54                  * 将字符串转为大写
55 56                  57                 toUpperCase: 58                      str.toUpperCase();
59 60 61             
62             调用
63             alert(lang.Math.abs(19)); 19
64             alert(lang.Math.PI);
65             alert(lang.String.toUpperCase(abcdefgABCDEFG
66             
67         68     69 >

 

二、面向对象的继承

先举个简单的例子来说一下JS中的继承,Student <extends> Person;

在js中,通过call来调用父类的构造方法继承父类属性(第33行),通过原型来继承父类方法(第39行)。注意:先调用父类构造函数,再添加自己的属性;先继承父类方法,再添加自己的方法

这里解释下为什么调用Person.call(this,name,sex)就相当于是在调用父类的构造方法:先问一下这个call中的this是谁?这里指向对象student吧。

所以,在子构造函数调用Person.call()时,那么构造函数Person里的两行代码this.name=name,this.sex=sex中this就是代表student了,所以这两行代码相当于是在为student添加name和sex属性

但是,下面的通过原型来继承父类方法,即Student.prototype = Person.prototype,是有问题的,这种方式将影响父类(继承是不能影响父类的),此时Person的原型中有了个showMajor方法(第50行),为什么呢?先思考下,下面解释。

="UTF-8" />
 4      6             
             * Person 父类             * @param {Object} name 姓名
             * @param {Object} sex 性别
11              12              Person(name,sex){
13                 .name  name;
.sex  sex;
            Person.prototype.showName =                 alert(.name); 
            Person.prototype.showSex 性别:.sex); 
21 22             
23         -----------------------------------------------------24             
25                          * Student   学生 继承 人
27              * @param {Object} name
             * @param {Object} sex
29              * @param {Object} major 学生特有属性:专业
30              31              Student(name,sex,major){
32                 调用父类的构造函数
                Person.call(34                 
35                 添加自己的属性
36                 .major  major;
37 38             继承父类原型中的方法
39             Student.prototype  Person.prototype;
40             添加自己特有的方法
            Student.prototype.showMajor 42 专业:.major);
44             
45              student new Student(bojiangzhou信息管理);
46             student.showName();
            student.showSex();
            student.showMajor();
49             
            alert(Person.prototype.showMajor);
51         52     53 >

第50行弹出的信息:

为了解释为什么通过Student.prototype = Person.prototype来继承父类方法会影响父类,下面举一个数组的例子,一看就知道怎么回事了。

为什么arr1和arr2弹出来的一样呢?第15、16行显示arr1和arr2是一个对象。对象!应该很清楚了吧,arr1和arr2都是指向这个数组对象的一个引用,所以改变arr2时,arr1也变了。

 5      6      7          arr1  [12345];
 8          arr2  arr1;
 9         
        arr2.push(611         
        alert(arr1); 弹出1,2,3,4,5,6
        alert(arr2); 14         
        alert(typeof arr1); object
 arr2); 17     18 >

其实我们主要是想获得arr1数组的一个副本,怎么做才能不改变arr1呢,看下面:

 [];
10         复制arr1的数据即可
11         for( i0;i<arr1.length;i++){
            arr2[i]arr1[i];
        }
16         
19         
20     21 >

同样的,我们也可以通过这种方式为继承的子类添加父类原型中的方法,而又不影响父类(38-41行):

39              p in Person.prototype){
                Student.prototype[p]  Person.prototype[p];
42             
43             44 47             
48             49 51 52             
53 54         55     56 >

第53行弹出信息:Person中没有showMajor方法了。

 

最后,以案例篇中最后给出的拖拽例子来应用下继承,那个拖拽有一个问题,就是没有控制拖拽出边界的问题。

先贴出之前的拖拽版本:

drag.js:

/* * 拖拽
 3  * @param {Object} id div的id
 4   5 function Drag(id){
this.oBox = document.getElementById(id);
 7     this.disX = 0;
 8     this.disY = 0 9     
10     var _this = this11     
12     this.oBox.onmousedown = 13         _this.fnDown();
14     }
15 }
16 //鼠标按下
17 Drag.prototype.fnDown = (ev){
18     var oEvent = ev || event;
19     
this.disX = oEvent.clientX - .oBox.offsetLeft;
21     this.disY = oEvent.clientY - .oBox.offsetTop;
22     
23     24     
25     document.onmousemove = 26         _this.fnMove();
27     };
28     document.onmouseup = 29         _this.fnUp();
30 31 32 鼠标移动
33 Drag.prototype.fnMove = 34     var oEvent= ev ||35     
36     this.oBox.style.left = oEvent.clientX - this.disX + 'px'37     this.oBox.style.top = oEvent.clientY - this.disY + 'px'38 39 鼠标抬起
40 Drag.prototype.fnUp = 41     document.onmousemove = null42     document.onmouseup = 43 }

drag.html:

style 6             div {
 7                 position: absolute;
}
 9         10         >拖拽11         script type="text/javascript" src="../js/drag.js" 12                     window.onload  drag1  Drag(Box115                 
16                 Box218         19     20 
bodydiv id="Box1" style="background: red;width: 200px;height: 200px;"div23     
24     ="Box2"="background: blue;width: 100px;height: 300px;"25 >

效果:可以看到红色和蓝色的都出边界了,但我们又不想去修改代码,那我们怎么做?学过java的应该都知道可以写一个子类来做一些更加具体的操作,又保留了父类功能,就是继承。

DragLimit.js:DragLimit继承自Drag,控制了不能出边界

 * 限制边界的拖拽,继承自Drag
 * @param {Object} id
 DragLimit(id){
 6     Drag.call( 7  8 继承方法
 9 for(var p in Drag.prototype){
10     DragLimit.prototype[p] = Drag.prototype[p];
11 12  * 覆写父类的鼠标移动方法,控制不能移出边界
14  15 DragLimit.prototype.fnMove = 16     17     
var left = oEvent.clientX - .disX;
var top = oEvent.clientY - .disY;
20     
控制边界
if(left < 023         left = 024     } else if(left > document.documentElement.clientWidth-.oBox.offsetWidth){
25         left = document.documentElement.clientWidth-.oBox.offsetWidth;
27     if(top <= 028         top = 029     } if(top > document.documentElement.clientHeight-.oBox.offsetHeight){
30         top = document.documentElement.clientHeight-.oBox.offsetHeight;
32     
33     this.oBox.style.left = left + 'px'this.oBox.style.top = top + 'px'35 }

dragLimit.html

            body                 padding 0                margin 9             13         14         15         16         ="../js/dragLimit.js" 17         19                 20                 
 DragLimit(23         25 
28     
29     >

效果:蓝色是不能移出边界的。

 

 三、JS中的对象

js中的对象分为本地对象、内置对象、宿主对象,这里给出W3School文档供参考:ECMAScript 对象类型

 

猜你在找的JavaScript相关文章