<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN">
<html>
<head>
<title>prototype.html</title>
<meta http-equiv="pragma" content="no-cache">
<meta http-equiv="cache-control" content="no-cache">
<meta http-equiv="expires" content="0">
<meta name="keywords" content="keyword1,keyword2,keyword3">
<meta name="description" content="this is my page">
<meta name="content-type" content="text/html; charset=UTF-8">
<!--<link rel="stylesheet" type="text/css" href="./styles.css">-->
<script type="text/javascript" src="../js/jquery-1.11.3.js"></script>
</head>
<body>
<div id="div"></div>
<script type="text/javascript">
// <![CDATA[
//$(document).ready(function() {
//});
//如果你需要在没有硬编码的window标识符下访问全局对象,你可以在任何层级的函数作用域中做如下操作:
var global = (function () {
return this;
})();
var count = 0;
function show(str) {
$("#div").append($("<p></p>").text("" + str));
}
//新创建对象的原型是从当前时刻函数的prototype属性获取的,这意味着同一个构造函数创建的两个对象的原型可以不同;
//这是因为构造函数的prototype属性也可以不同。
//function.funcName声明的是static函数
function BaseClass() {
this.name = "BaseClassName";
this.showMsg = function() {
show("BaseClass::showMsg::" + this.name);
};
this.baseShowMsg = function() {
show("BaseClass::baseShowMsg::" + this.name);
};
}
BaseClass.showMsg = function() {
show("BaseClass::showMsg static name = " + this.name);
};
function ExtendClass() {
this.name = "ExtendClassName";
this.showMsg = function () {
show("ExtendClass::showMsg::" + this.name);
};
}
ExtendClass.showMsg = function() {
show("ExtendClass::showMsg static name = " + this.name);
};
//通过prototype实现继承
ExtendClass.prototype = new BaseClass();
//设置constructor
ExtendClass.prototype.constructor = ExtendClass;
var instance = new ExtendClass();
instance.showMsg(); //ExtendClass::showMsg::ExtendClassName
//相当于instance.__proto__.baseShowMsg() this指向instance
instance.baseShowMsg(); //BaseClass::baseShowMsg::ExtendClassName
ExtendClass.prototype.showMsg(); //BaseClass::showMsg::BaseClassName
ExtendClass.prototype.showMsg.call(instance); //BaseClass::showMsg::ExtendClassName
//static方法调用,BaseClass.__proto__是Function.prototype
//this指向function类型的BaseClass对象,
show(BaseClass.__proto__ == Function.prototype); //true
//static方法的this指向fuction本身,fuction名称本身是Function的实例
BaseClass.showMsg(); //BaseClass::showMsg static name = undefined
ExtendClass.showMsg(); //ExtendClass::showMsg static name = undefined
//创建对象之后修改构造函数的原型对象(不是替换),指向的还是同一个原型对象,则所有修改前后创建的对象都指向修改后的原型对象。
ExtendClass.prototype.baseShowMsg = function() { show("prototype::baseShowMsg"); };
instance.baseShowMsg(); //prototype::baseShowMsg
var str = "";
for(var key in ExtendClass.prototype) {
str += key;
str += "=";
str += ExtendClass.prototype[key];
show(str);
str = "";
}
//name=BaseClassName
//showMsg=function() { show("BaseClass::showMsg::" + this.name); }
//baseShowMsg=function() { show("prototype::baseShowMsg"); }
//constructor=function ExtendClass() { this.name = "ExtendClassName"; this.showMsg = function () { show("ExtendClass::showMsg::" + this.name); }; }
//创建对象之后替换构造函数的prototype,已创建的对象继续指向原来的prototype对象,此时修改前后的对象的__proto__不再是同一个对象。
ExtendClass.prototype = new BaseClass();
var instance1 = new ExtendClass();
//替换原型对象
ExtendClass.prototype = {id : "json", baseShowMsg : function() { show("json::baseShowMsg"); }};
show(instance1.id); //undefined
instance1.baseShowMsg(); //BaseClass::baseShowMsg::ExtendClassName
//instance2指向新的原型对象
var instance2 = new ExtendClass();
show(instance2.id); //json
instance2.baseShowMsg(); //json::baseShowMsg
//对象独立于构造函数,构造函数完成了自己的主要工作(创建对象)以后可以删除。原型对象通过引用__proto__属性继续存在
ExtendClass.prototype = new BaseClass();
var instance3 = new ExtendClass();
show(instance3.id); //undefined
//为原型对象增加属性
ExtendClass.prototype.id = "new id";
ExtendClass.prototype.func = function() { show("new.func() invoked"); };
show(instance3.id); //new id
instance3.func(); //new.func() invoked
//instanceof操作符是和原型链一起工作的,而不是构造函数
ExtendClass.prototype = new BaseClass();
var instance4 = new ExtendClass();
show(instance4 instanceof BaseClass); //true
ExtendClass.prototype.id = "new id";
show(instance4 instanceof BaseClass); //true
ExtendClass.prototype = {id : "json", baseShowMsg : function() { show("json::baseShowMsg"); }};
show(instance4 instanceof BaseClass); //true
//instance4是ExtendClass创建的对象,instanceof是比较prototype是否在同一个原型链上
show(instance4 instanceof ExtendClass); //false
var instance5 = new ExtendClass();
show(instance5 instanceof BaseClass); //false
//Object.prototype.hasOwnProperty(attr):判断一个对象是否包含自定义属性而不是原型链上的属性
var foo = {
value : 42,
method : function() {}
};
show(foo.hasOwnProperty("value")); //true
show(foo.hasOwnProperty("method1")); //false
//JavaScript 不会保护 hasOwnProperty 被非法占用,因此如果一个对象碰巧存在这个属性,就需要使用外部的 hasOwnProperty 函数来获取正确的结果。
show(Object.prototype.hasOwnProperty.call(foo, "method")); //true
// ]]>
</script>
</body>
</html>