JavaScript面向对象的简单介绍
作者:killercat 来源:killercat 发布时间:2008-06-27 12:37:00
JavaScript是一门OOP,而有些人说,JavaScript是基于对象的。
1) 如何创建对象:
1. 使用constructor,例如:
var obj = new Object() // var 可以省略
var obj = new Date()
2. 使用对象字面值(object literals),例如:
程序代码
var obj = "123" // 创建一个String对象
var obj = /^abc$/ //创建一个RegExp对象
更加复杂的情况是,我们可以直接生成一个自定义的只有属性的对象:
程序代码
var obj = {
name:"killercat",
home:"www.i170.com/user/killercat"
}
document.write(obj.name+"<br />")
document.write(obj.home)
结果:
killercat
www.i170.com/user/killercat
2) JavaScript中的属性:
str = "www.i170.com/user/killercat" // str 一个字符串对象的引用
document.write(str.length)
通过对象的引用加上"."再加上属性名,可以访问到这个属性,也可以修改这个属性,甚至是添加一个属性,比如:
var obj = new Object()
obj.name = "killercat" // 为对象直接添加一个属性
document.write(obj.name) // 访问对象的属性
obj.name = "kcat" // 修改对象的属性
document.write(obj.name)
枚举属性值:
使用 for ... in 语句可以枚举属性(具体来说就是枚举属性名),前面已经提到过,比如
for(ele in window){
document.write(ele+"<br />")
}
如何得到属性值?
obj = new Object()
obj.p1 = "a"
obj.p2 = "b"
obj.p3 = "c"
for(ele in obj)
document.write(obj.ele) // 这是新手可能犯的错误,obj.ele 的值是undefined
应该这样访问属性值:
document.write(eval("obj."+ele))
未定义的属性:
obj = new Object()
document.write(obj.name)
结果是:undefined
删除属性:
obj = new Object()
obj.name = "killercat"
delete obj.name
document.write(obj.name)
结果是:undefined
理解属性:
我们知道在Java,c++中,属性要么属于某个类(类属性或说是静态属性),要么属于对象,也就是说,同一个类的对象,一定有一样的属性,但是JavaScript不一样,同样是Object的对象,却可以有不同的属性。除了这类的属性,JavaScript中还有静态的属性(变量)。
3) Constructor
源于某些未知原因,有些人似乎不愿意在JavaScript提到classes这个词,取代的是"对象的类型(object types)",甚至有些人直接叫函数,于是可以看见这样的说法:“我们通过预先定义好的函数,产生了一个对象”。本文使用类,这个名词。
JavaScript 定义方法的方式和定义类的方式一模一样:
function User(name,sex){ // 定义了类 User
this.name = name;
this.sex = sex;
}
user = new User("kc","man")
document.write(user.name+"<br />"+user.sex)
contructor的作用就是在初始化属性(变量)
4) 方法
源于某些未知原因,有些人似乎不愿意在JavaScript
以下例子引用于<<__JavaScript: The Definitive Guide>>
function Rectangle_area( ) { return this.width * this.height; }
function Rectangle_perimeter( ) { return 2*this.width + 2*this.height; }
function Rectangle_set_size(w,h) { this.width = w; this.height = h; }
function Rectangle_enlarge( ) { this.width *= 2; this.height *= 2; }
function Rectangle_shrink( ) { this.width /= 2; this.height /= 2; }
function Rectangle(w, h)
{
this.width = w;
this.height = h;
this.area = Rectangle_area;
this.perimeter = Rectangle_perimeter;
this.set_size = Rectangle_set_size;
this.enlarge = Rectangle_enlarge;
this.shrink = Rectangle_shrink;
}
这种风格可能和Java,c++很不同。方法中的this表示调用它的对象的引用。
5) prototype
prototype是一个对象,每个类都包含一个prototype对象(注意,每个类一个,而不是每个对象一个)。
看看下面的例子:
function User(name)
{
this.name = name
}
User.prototype.name = "killercat" // 类名.prototype.属性(或方法)
user = new User("who"+"<br />")
document.write(user.name)
delete user.name
document.write(user.name)
再看一个例子:
function User(name)
{
}
User.prototype.name = "human"
user1 = new User()
user2 = new User()
document.write(user1.name+"<br />")
document.write(user2.name)
结果:
human
human
说明了,每个类一个prototype对象,而不是每个对象单独一个。
obj.x 这条语句的查找顺序是,先在obj中找x属性,假如没有,再进入obj对应的类中找prototype.x,对于方法来说,也一样。因此,不要出现这样的语句: user.prototype.name = "xxx" 必须是 user.name = "xxx" (prototype对象属于一个类,而不是一个对象)
类名.prototype.属性 // 相当于一个实例变量(属性),对方法也一样
类名.属性 // 相当于一个静态变量(属性),对方法也一样,调用的时候必须使用"类名.属性",不能使用"类对象.属性",因为它属于一个类,而不是一个对象。
例如:
function User(name)
{
this.name = name
}
User.type = "human"
user = new User("kc")
document.write(User.type + "<br />")
document.write(user.type)
结果:
human
undefined
另外,每个prototype都有一个constructor属性,默认用于保存constructor的定义,例如上面的user对象,调用:
user.constructor得到:
function User(name) { this.name = name; }
我们可以通过typeof,知道参数的类型,假如是对象,就返回"object",假如是方法就返回"function"
6) 利用prototype实现类间的继承,例如:
// 父类
function Circle(r){
this.r = r;
}
Circle.PI = 3.14;
Circle.prototype.getArea = function (){
return Circle.PI * this.r * this.r;
};
Circle.prototype.toString = function (){
if(( typeof this == "object") && (this.constructor == Circle)){
return "circle with a radius " + this.r ;
}
else{
return "unknown object";
}
};
Circle.max = function (c1,c2){
return c1.r >= c2.r ? c1 : c2;
};
// 子类
function ColorCircle(r,color){
this.r = r;
this.color = color;
}
ColorCircle.prototype = new Circle(0); // 保存父类的对象
ColorCircle.prototype.constructor = ColorCircle; // 为constructor 改名字
ColorCircle.prototype.toString = function(){
if(( typeof this == "object") && (this.constructor == ColorCircle)){
return this.color+" circle with a radius " + this.r ;
}
else{
return "unknown object";
}
}
ColorCircle.prototype.getColor = function(){
return this.color;
}
ColorCircle.prototype.setColor = function(color){
this.color = color;
}
也就是,使用prototype保存父类的对象,在构造子类的时候,父类对象同时被构造(因为prototype被构造)。也就是JavaScript继承其实就是让子类的prototype对象保存父类的对象。


猜你喜欢
- 前言本文的github仓库地址为: 替换照片人物背景项目(模型文件过大,不在仓库中)由于模型文件过大,没放在仓库中,本文下面有模型下载地址。
- Python的五个标准数据类型数字字符串列表元组字典一、数字不可变数据类型,存储值为数值1.创建对象,分配数值例:>>>
- 对于SQL的Join,在学习起来可能是比较乱的。我们知道,SQL的Join语法有很多inner的,有outer的,有left的,有时候,对于
- 前言启动页在APP中是个很常见的需求,为什么对于小程序来说也非常重要呢?首先我描述一下我在开发过程中遇到的一些问题以及解决的步骤,到最后为什
- 本文介绍了深入理解ES6中let和闭包,分享给大家,具体如下:在开始本文之前我们先来看一段代码for(var i=0;i<10;i++
- 本文实例介绍了python实现井字棋游戏的方法,分享给大家,具体内容如下windows7下python3.4.0编译运行通过。由于采用了cm
- 如下所示:from kafka import KafkaClientfrom kafka.producer import SimplePro
- 一、前言Celery是一个基于python开发的分布式任务队列,而做python WEB开发最为流行的框架莫属Django,但是Django
- MS SQL性能是很不错的,但是数据库用了一段时间之后,数据库却变得很大,实际的数据量不大。一般都是数据库日志引起的!数据库日志的
- 一、内置函数下面简单介绍几个:1.abs() 求绝对值2.all() 如果 iterable 的所有元素都为真(或者如果可迭代为空),则返回
- 常用功能 mean(data)mean(data)用于求给定序列或者迭代器的算术平均数。import statisticsexample_l
- 格式良好的SQL并不会比乱七八糟的SQL运行效果更好。数据库其实不怎么关心SQL语句中你把逗号放到了字段名的前面还是后面。为了你自己思路清楚
- 这是通过博主写的英雄联盟下载器下载的部分的英雄皮肤,可以看一下效果。每个英雄的皮肤的会自动根据英雄名称创建相应的文件夹存放。实现思路比较简单
- Python 正则表达式简介正则表达式是一个特殊的字符序列,它能帮助你方便的检查一个字符串是否与某种模式匹配。Python 自1.5版本起增
- 目录代码分享一、安装并创建Scrapy项目二、爬取应用市场评论过程1. Scrapy爬虫运行流程2. 页面分析页面分析过程一页面分析过程二页
- 关于 pynput pynput 可以监控我们的键盘和鼠标。目前具有此类功能的库有很多,比如 pygame 等游戏库,但是当我们只需要
- 众所周知,Python开发框架大大减少了开发者不必要的重复劳动,提高了项目开发效率的同时,还使得创建的程序更加稳定。目前比较主流的Pytho
- 1、从Kmeans说起Kmeans是一个非常基础的聚类算法,使用了迭代的思想,关于其原理这里不说了。下面说一下如何在matlab中使用kme
- 概述从今天开始我们将开启一段自然语言处理 (NLP) 的旅程. 自然语言处理可以让来处理, 理解, 以及运用人类的语言, 实现机器语言和人类
- 调用pytorch内置的模型的方法import torchvisionmodel = torchvision.models.resnet50