JavaScript 面向对象-封装

封装

两种封装方式

函数封装
<!DOCTYPE html>
<html lang="en">
<head>
	<meta charset="UTF-8">
	<title>函数封装</title>
</head>
<body>
	<script type="text/javascript">
		(function(){

			var a = 3;
			var b = 4;
			function fn1(){
				console.log(a);
			};

			function fn2(){
				console.log(b);
			}

			/**
			 * 函数封装的缺点是
			 * 		1.所有函数暴露在全局变量中,容易产生污染问题
			 * 		2.代码冗余,结构不清晰
			 *
			 * 		*** 解决办法
			 * 			对象封装法
			 */
		})()
	</script>
</body>
</html>
对象封装
<!DOCTYPE html>
<html lang="en">
<head>
	<meta charset="UTF-8">
	<title>对象封装</title>
</head>
<body>
	<script type="text/javascript">
		(function(){
			var obj = {

				// 这里放代码的方法
				fn1 : function(){
					console.log(1);
				},
				fn2 : function(){
					console.log(2);
				}
				// 这里放代码的属性

				/**
				 * 对象封装的优点 - 解决了函数封装的问题
				 * 		1.全局只有obj这一个全局变量
				 * 		2.代码结构清晰
				 */
			}
		})()
	</script>
</body>
</html>

对象的几种创建方式

1. 对象字面量
<!DOCTYPE html>
<html lang="en">
<head>
	<meta charset="UTF-8">
	<title>对象字面量</title>
</head>
<body>
	<script type="text/javascript">
		(function(){
			/**
			 * 字面量创建对象
			 * 		缺点
			 * 			每次只能创建一个对象,重复性较多,代码冗余
			 * 			
			 */
			var o = {
				fn1 : function(){
					console.log(1);
				}
			};

			o.fn1();	// 1
		})()
	</script>
</body>
</html>
2. new内置构造函数
<!DOCTYPE html>
<html lang="en">
<head>
	<meta charset="UTF-8">
	<title>new内置构造函数</title>
</head>
<body>
	<script type="text/javascript">
		(function(){
			/**
			 * new内置构造函数
			 * 		缺点
			 * 			每次只能创建一个空对象,需要重复性的给对象赋值属性和方法
			 */
			var o = new Object();
			o.name = "jianyan";
			o.age = 24;
			o.say = function(){
				console.log(this.name);
			}
			console.log(o.name);	// jianyan
			console.log(o.age);		// 24
			o.say();				// jianyan
		})()
	</script>
</body>
</html>
3. 工厂函数
<!DOCTYPE html>
<html lang="en">
<head>
	<meta charset="UTF-8">
	<title>工厂函数</title>
</head>
<body>
	<script type="text/javascript">
		(function(){
			/**
			 * 工厂函数
			 *
			 * 		缺点,每次实例化的属性和方法都一样,如何解决?
			 * 		解决,自定义构造函数
			 */
			function creatObj(){
				var obj = new Object();
				obj.name = "jianyan";
				obj.age = 24;
				obj.say = function(){
					console.log(this.name);
				}
				return obj;
			}

			// 实例化
			var o1 = creatObj();
			var o2 = creatObj();

			o1.say();
			// 缺点,每次实例化的属性和方法都一样,如何解决?
			// 		解决,属性传参和方法分离

			function creatObj1(name,age){
				var obj = new Object();
				obj.name = name;
				obj.age = age;
				obj.say = say1;
				return obj;
			}
			function say1(){
				console.log(this.name);
			}
			var o3 = creatObj1("jianyan",24);
			var o4 = creatObj1("qian",25);
			console.log(o3.name);	// jianyan
			console.log(o4.name);	// qian
		})()
	</script>
</body>
</html>
自定义构造函数
<!DOCTYPE html>
<html lang="en">
<head>
	<meta charset="UTF-8">
	<title>自定义构造函数</title>
</head>
<body>
	<script type="text/javascript">
		(function(){
			/**
			 * 自定义构造函数
			 * 		函数名首字母大写
			 *
			 *		问题
			 *			所有方法都暴露在全局变量
			 *			代码结构不清晰,代码冗余
			 *		解决
			 *			使用原型
			 */
			
			function CreateObject(name,age){
				// var this = new Object()	浏览器默认创建
				this.name = name;
				this.age = age;
				this.say = say;
							/*function(){
					console.log(this.name);
				}*/
				// return this;		浏览器默认创建
			}
			function say(){
				console.log(this.name);
			}

			// 实例化
			var o1 = new CreateObject("jianyan",24);
			var o2 = new CreateObject("qian",25);

			console.log(o1.name);	// jianyan
			console.log(o2.name);	// qian

		})()
	</script>
</body>
</html>
原型

    <!DOCTYPE html>
<html lang="en">
<head>
	<meta charset="UTF-8">
	<title>原型</title>
</head>
<body>
	<script type="text/javascript">
		(function(){
			/**
			 * 原型
			 * 		什么是原型?
			 * 			在创建构造函数时,此时系统会默认创建并关联一个对象,这个对象就是原型.
			 * 			默认的原型对象中有一个constructor属性执行该构造函数
			 *
			 * 		原型的作用?
			 * 			原型是一个对象,其属性和方法可以被构造函数创建的实例使用
			 * 			***  实例可以直接访问原型内的属性和方法
			 *
			 * 		如何给原型对象添加属性和方法?
			 * 			1. prototype
			 *    			构造函数名.prototype.say = function(){} 给原型添加一个say方法
			 *    		2. 直接替换原型对象
			 *    			直接替换原型对象,此时会导致 构造函数,实例,原型对象三者关系改变
			 *    			之前的原型对象也会失效
			 *    			*** 小心使用,注意三角关系
			 *
			 * 		原型是使用注意事项
			 * 			1.使用对象访问属性,先去其构造函数中查找属性,若有,返回属性,没有就会去原型对象查找
			 * 			2.使用对象设置属性,只在对象中查找,若没有,则创建属性,若有,则覆盖属性
			 * 			3.如果在原型对象中有引用类型的属性,那么使用对象进行修改该属性内容
			 * 				*** 我们一般讲共享的方法放在原型,属性放在对象中
			 *
			 * 		__proto__ 调试用
			 * 				隐式原型,一个对象的隐式原型指向构造该对象的构造函数的原型,
			 * 				这也保证了实例能够访问在构造函数原型中定义的属性和方法。
			 *
			 * 		替换原型注意
			 * 			在新替换的原型中,,没有constructor属性,就会影响三角关系
			 * 			所以,新替换原型后,最好手动添加constructor属性,以保证三角关系的稳定
			 *    		
			 *    		Object.getPrototypeOf() 
			 *    			检测某个实例是否是另一个对象的原型对象
			 * 			
			 *    		
			 * 
			 */
			var o = new Object();
			console.log(o.__proto__ === Object.prototype);
			console.log(Object.__proto__ == Function.prototype);
			console.log(Function.prototype.__proto__ == Object.prototype);
			console.log(Number.__proto__ == Function.prototype);
		})()
	</script>
</body>
</html>

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值