JS面向对象
面向对象主要内容:
1.属性
事务的特性
2.方法
事务的功能
3.对象
事物的一个实例
prototype:原型--内存地址 存储一个对象
prototype属于object子对象
函数构造函数,函数构造器,创建函数对象
var obj = new Function(var1,var2,……,functionBody());
//var1,var2正常交流 functionBody()自定义函数
//注意:构造器构造的对象,效率低,var1,var2顺序在functionBody中不可以变
闭包:
闭包是一个拥有了许多变量和绑定了这些变量的环境的表达式(通常是一个函数)
变量作用域两种:全局作用域,局部作用域
全局变量在函数内部可以访问
在函数内,用var声明的都是局部变量
闭包:
特点:函数b 是在a内嵌套的 函数a需要返回函数b
用途:1.读取函数内部变量2.让i变量的值 保留在内存中
闭包的优缺点:
优点:有利于封装,可以访问局部变量
缺点:1.内存占用时间比较长,浪费内存,容易产生内存泄漏
声明对象的方式:
1.
var person={
name:’zhangsan’,
age:26,
eat:function(fds){
alert(“我在吃”);
},
play:function(ga){
alert(“playing game”);
}
}
person.name//调用属性
person.eat(“面条“);
2.new操作符后跟Object构造函数
var obj = new Object();
obj.属性=属性值;
obj.属性=属性值;
obj.方法=function(str){
方法代码
};
3.js中构造函数方法声明对象
function test([参数列表]){
this.属性=属性值;
this.方法=function(){
方法代码
}
}
var obj = new test(参数列表);
this代表当前对象,实力化的哪一个
4.js中工厂方式声明对象
function createObject(name,age){
var obj = new Object();
obj.name = name;
obj.age = age;
obj.run = function(){
return this.name + this.age +’运行中….’;
};
return obj;
}
var box1 = createObject(‘zhangsan’,100);
var box2 = createObject(‘lisi’,200);
同种模式创造出来的对象是相对独立的
如何运行
载入内存准备执行
构造方式不会显示创建对象,将属性赋值给this,不需要return对象
工厂必须在方法内部创建object对象,还需要返回object对象,属性和方法都是赋给object对象的
5.js中原型模式声明对象:
function test(){
}
test.prototype.属性 =属性值;
test.prototype.属性=属性值;
test.prototype.方法名 =function(){
执行代码
}
var obj = new test();
函数本身声明为空内容,利用prototype定义一些属性和方法
让所有实例对象都拥有它包含的属性和方法
test.prototype instanceof Object 是对的
function test(){
}
test.prototype.color = “red”;
test.prototype.heights=“1.7”;
test.showInfo=function(){
alert(this.color+this.height);
}
test.getinfo=function(){
altert(“aaa”);
}
var car1 = new test();
car1.getinfo();
原型模式还可以:
function test(){
}
test.prototype={
color: “red”;
…..
}
6.混合模式
function test(v1,v2,v3){
this.v1 = v1;
this.v2 = v2;
this.v3 = v3;
}
test.prototype.方法名称 = function(){
执行代码
}
var obj = new Blog (v1,v2,v3);
e.g.
function blog(name,url,friend){
this.name = name;
this.url = url;
this.friend = friend;
}
blog.prototype={
showinfo:function(){
alert(this.name+this.url);
}
gets:function(){
alert(this.friend);
}
}
var peo = new blog(“”,””,””);
peo.showinfo();**
对象的遍历
var ren = {};
遍历对象的属性,对象可以当作数组处理 for in
ren.name =“zhangsan”;
ren.age=18;
ren.len=“1.80”;
ren.demo=function(){
alert(this.name);
}
for(var i in ren){
alert(ren[i]);//取的是属性的值或者是方法的代码
}
i是属性或者方法的名称
构造函数的话:
function ren(){
this.name=“zhangsan”;
this.age=“19”;
this.demo = function(){
alert(this.name);
}
}
var r = new ren()
for(var i in r){
alert(r[i]);
}
对象的存储
对象放在栈内存中,指向堆内存中的地址
堆内存中包含所有的属性和方法,但是如果是方法的话,方法中会有需要执行的代码,那些代码会被放置在代码段中
所以所有的对象之间都是相互独立的
封装
把对吸纳高内部数据和操作细节进行隐藏
只对外提供调用的接口
js中可以通过闭包实现封装
所以最佳选择就是函数作用域
e.g.1
function demo(){
var n =1;
function test(){//特权方法
return ++n;
}
return test;
}
var at = demo();
具有真正的封装的意义
e.g.2
function A(){
function _xx(){alert(11);}
this.xx=function(){
return_xx;
}
}
A.prototype={
oth:function(){
alert(“普通方法”);
}
}
var a = new A();
var b = a.xx();
b();//print 11
原型和原型链
原型:是利用prototype添加属性和方法
原型链:js在创建对象的时候,都会有一个叫做proto的内置属性,用于指向创建它的函数对象的原型对象prototype
js继承:
的过程:
var person = function(){};
var p = new person();//三个阶段
1.var p ={}//创建对象
2.p._proto_=person.prototype _proto_自带的一个属性
3.创建对象(初始化对象)p———>person.call(p)
e.g.
</head>
<script type = “text/javascript”>
//js继承
var person = function(){}
person.prototype.say=function(){
alert(“天气很好”);
}
var p = new person();
p.say();//p没有say方法
//p._proto_=person.prototype(有这个属性)----有say方法了
person.prototype.gongzi = 500;
var programmer = function(){};
programmer.prototype = new person();
programmer.prototype.scd = function(){
alert(“明天天气也不错“);
}
programmer.prototype.gongzi=1000;
var p = new programmer();
p.say();//可以调用
p.wcd();
alert(p.gongzi);//1000;
//原型链实现过程
var p = new programmer();
p._proto_ = programmer.prototype = new person();
var p1 = new person();
programmer.prototype = p1
p.say();——>p._proto_—>programmer.prototype ==p1——>p1._proto_==person.prototype.say();
当两个都有同样的属性时,比如gongzi这个,子的会覆盖父的
关键词
js面向对象的关键词
1.instanceof:变量是否是一个对象的实例
var arr = new Array();
alert(arr instanceof Array);
2.delete:删除对象属性变成undefined,不可以删除方法⚠,也不可以删除变量,也不可以删除原型链中的属性和方法
3.call,apply:对象默认带有
call只可以引用已经存在的对象
add.call(subs,5,3);
括号里的是被替换的,subs-->add
add.apply(sub,[5,3]);
e.g.
function animal(){
this.name = “ani”;
this.showName = function(){
alert(this.name);
}
}
function cat(){
this.name = “cat”;
}
var an = new animal();
var c = new cat();
an.showName.call(c,”,”);//cat,通过call方法将showName方法传递给了cat使用
真正的实例话中的例子的话,把对象里面的方法传递给后面的对象使用
4.arguments:
每个函数都有一个arguments对象的实例arguments,引用函数的参数(实参)
可以用数组下标方式引用arguments元素
argument.length参数个数
arguments.callee引用函数自身
arguments如果表示参数,可以遍历
5.callee:
返回正在执行的function对象,function内容
arguments.callee 默认值,正在执行的function对象
callee当作属性,函数内容
不可以加括号
6.this的使用方法
1.this函数调用
function test(){
this.x=1;//this全局变量 global
alert(this.x);
}
text();
等于:
var x = 1;
function test(){
this.x = 0;//改变了全局变量的值
}
text();
alert(x);//0
2.作为方法调用
构造函数内 this指当前对象
function test(){
this.name = “zhangsan”;//this表示当前对象
this.age=18;
}
var t = new test();
alert(t.name);
3.call和apply 中this指向第一个参数
var x = 0;
function test(){
alert(this.x)
}
var o ={};
o.x=1;
o.m=test
o.m.apply();//0
o.m.apply(o);//1
对象冒充
将父类的属性和方法一起传给子类,做一个对象冒充
//对象冒充
function person(name,age){
this.name = name;
this.age = age;
function sayHi = function(){
alert(“hi”);
}
}
person.prototype.walk = function(){
alert(“walk….”);
}
function student(name,age,grade){
this.newMethod = person;//冒充person对象,传递特权属性和特权方法给子类
this.newMethod(name,age);
this.grade = grade;
}
var s1 = new student(“zhangsan”,15,5);//s1是student对象,继承person,拥有person所有属性和方法
alert(s1.name);
s1.walk();//wrong
对于对象冒充,特权属性是没有问题的,只是继承了特权属性
没有继承共有方法和属性
构造函数的继承
在子类内部构造父类的对象实现继承
function parents(name){
this.name = name;
this.say = function (){
alert(“father’s name”);
}
}
function child(name,age){
this.pObj = parents;
this.pObj(name);
this.age = age;
this.sayC = function(){
alert(“child”+this.name+”—-“+”age:”+this.age);
}
}
var p = new parents(“zhangsan”);
p.say();//父亲的名字是shangsan
var c = new child(“李四“,20);
c.sayC();//this.pObj(name);———parents(name)——-this.name=name=“李四”
父对象被子对象继承,所有的属性和方法,都传递到了子对象中
call和apply的用法
call是调用一个对象的一个方法,以另一个对象替换当前对象
apply:应用某一对象的一个方法,用另一个对象替换当前对象
call—obj.call(方法,var1 ,var2…….)
apply—obj.apply(方法,[var1,var2,….]);
function person(name,age,len){
this.name = name;
this.age=age;
this.len = len;
this.say = function(){
alert(this.name+”:”+this.age+”:”+this.len);
}
}
function student (name,age)[
person.call(this,name,age);
}
var person = new person(“张三“,25,”170”);
per.say();
var stu = new student(“李四”,18);
stu.say();//李四 18 undefined//person.call里的this变成了stu
apply继承:
function teacher(name,len){
person.apply(this.[name,age,len]);
}
var tea = new teacher(“…”,”…”,”…”);
tea.say();//… … …
**粗体** _斜体_ [链接](http://example.com) `代码` - 列表 > 引用
。你还可以使用@
来通知其他用户。