JS高级学习路线——面向对象进阶
构造函数进阶
使用构造函数 创建对象
用于创建对象 其除了是一个函数之外,我们又称之为构造对象的函数 - 简称构造函数
function Product(name,description){
//属性
this.name=name;
// 属性
this.description = description
//方法 又称方法属性 万物皆属性
this.buy=function(){
alert('buy')
}
}
//会拷贝一份
var p1 = new Product()
var p2 = new Product()
//实例p1,p2的构造函数是谁
console.log(p1.constructor)
console.log(p2.constructor)
如何判断某个实例是否是根据某个构造函数创建的
if(p1 instanceof Product){
alert('true')
}
存在的问题
每个实例的name,描述确实不一样,需要单独的空间存储,但是buy方法是所有实例都一样的
为了避免内存浪费,所以出现了原型帮助我们解决这个问题
原型对象 不管你实例化多少次,都只生成一次
四种创建方式
1.传参形式
2.默认值
3.动态添加形式
4.混合模式
函数声明和函数表达式的区别
搭积木开发 -- 代码可读性极高
//产品对象
/*类 -- 抽象对象*/
function Product(name,price) {
/*属性 行为 可以为空或者给默认值*/
this.name=name
this.price=0;
/*我们的需求:自动计算打折后的价格*/
/*形象的理解:包装*/
Object.defineProperty(this, "price", {
get: function () {return price*0.9;},
set: function (value) {
/*大概普通产品的价格都在0--1万*/
if(value>10000)
{
alert('产品价格必须在0--1万之间');
}else{
price = value;
}
}
});
} //定义对象的两种方式
Product.prototype={
getPrice:function() {
return this.price
},
addToCart:function(){
alert('将物品添加到购物车')
}
} Product.prototype.buy=function(){}
Product.prototype.addToCart=function(){} /*获取元素*/
var btn = document.getElementById('btn')
var name = document.getElementById('pname') window.onload=function() {
/*实例化 -- 实例 -- 具体*/
//如何使用
//对象的使用必须先实例化,对象定义好之后,都是抽象的,必须实例化成具体
var iphone = new Product() /*给对象的赋值赋值,也可以新增属性*/
iphone.name='iphone7'
iphone.price=6000 /*绑定元素*/
/*通过点语法访问对象中的属性或者方法*/
name.innerHTML=iphone.name
price.innerHTML=iphone.price /*绑定事件*/
btn.onclick = function(){
iphone.addToCart()
}
}
对象属性进阶1 get set权限
产品对象
1.对象内如何使用对象的属性和方法:this
2.对象外如何使用:先实例化,后用点语法
类 -- 抽象对象
function Product(name,price) {
/*属性 行为 可以为空或者给默认值*/
this.name=name
this.price=0;
this.description = '';
this.zhekou = ''
this.sales = ''
/*我们的需求:自动计算打折后的价格*/
/*形象的理解:包装*/
Object.defineProperty(this, "price", {
get: function () {return price*0.9;},
set: function (value) {
/*大概普通产品的价格都在0--1万*/
if(value>10000)
{
alert('产品价格必须在0--1万之间');
}else{
price = value;
}
}
});
}
get set 日期 拓展性知识
Object.defineProperty(this, "produceDate", {
get: function () {
return dateFormat(produceDate,'yyyy-MM-dd');
},
set: function (value) {
produceDate = value;
}
});
function dateFormat(date,format) {
var o = {
"M+" : date.getMonth()+1, //month
"d+" : date.getDate(), //day
"h+" : date.getHours(), //hour
"m+" : date.getMinutes(), //minute
"s+" : date.getSeconds(), //second
"q+" : Math.floor((date.getMonth()+3)/3), //quarter
"S" : date.getMilliseconds() //millisecond
}
if(/(y+)/.test(format)) format=format.replace(RegExp.$1,
(date.getFullYear()+"").substr(4- RegExp.$1.length));
for(var k in o)if(new RegExp("("+ k +")").test(format))
format = format.replace(RegExp.$1,
RegExp.$1.length==1? o[k] :
("00"+ o[k]).substr((""+ o[k]).length));
return format;
}
权限的设置——可读
/*我们的需求:自动计算打折后的价格*/
Object.defineProperty(this, "price", {
value:5000000,
writable: t,
});
对象属性进阶2 公有私有属性
对象构造函数
// 私有属性好处: 安全 就类似闭包中的函数一样 减少污染
function Person(name) {
//私有属性,只能在对象构造函数内部使用
var className = "用户对象";
//公有属性,在对象实例化后调用
this.name = name;
//私有方法
var privateFunction = function () {
alert(this.name);
}
//公有方法
this.publicFunction = function () {
alert(this.name); //公有属性
alert(className); //正确 直接通过变量名访问
alert(this.className); //undefined 错误 不能这样访问
}
//公有属性
alert(className);
//正确 直接通过变量名访问
alert(this.className); //undefined 错误 不能这样访问
}
什么是公有属性:
使用象的人可以访问到对象内部的某个属性
init函数的引入
Product.prototype={
/*初始化函数的引入*/
/*我们将开发某个功能的初始化的工作都放在一起函数里面,用户只需要只要这一个工具就可以了*/
init:function(){
this.bindDOM()
this.bindEvents()
},
bindDOM:function(){},
bindEvents:function(){}
}
私有成员的引入
//产品对象
/*类 -- 抽象对象*/
function Product(name,price) {
/*属性 行为 可以为空或者给默认值*/
this.name=name
this.price=1000;
this.description = '';
this.produceDate
/*我们的需求:自动计算打折后的价格*/
Object.defineProperty(this, "price", {
value:5000000,
writable: false,
});
var that = this;//改变this指向
function bindDOM(){
/*获取元素*/
var btn = document.getElementById('btn')
var name = document.getElementById('pname')
/*绑定元素*/
/*通过点语法访问对象中的属性或者方法*/
name.innerHTML=that.name
price.innerHTML=that.price
}
function bindEvents(){
var btn = document.getElementById('btn')
/*绑定事件*/
btn.onclick = function(){
that.addToCart()
}
}
this.init = function(){
/*访问方式:不加this*/
bindDOM()
bindEvents()
}
}
//定义对象的两种方式
Product.prototype={
getPrice:function() {
return this.price
},
addToCart:function(){
alert('将物品添加到购物车')
}
}
config
var that = this;
//定义一个变量 :这个变量可以被对象中所有的属性访问到。。。。
/*避免重复,减少内存*/
/*统一管理*/
this.config = {
btnConfirm: document.getElementById('btn'),
btnBuy: document.getElementById('btn'),
sum : 1000,
des : document.getElementById('pdes'),
youhuijia : document.getElementById('pyouhui'),
zhekou : document.getElementById('pzhekou')
}
function bindDOM(){
that.config.name.innerHTML=that.name
}
对象实例进阶
数据类型的复习
//数值型
var num1 = 1;
//字符串型
var num2 ='2333fgfgfggggggggggggggggggggg';
//布尔型
var num3 =false;
//对象型
var num4 = document.getElementById('mydiv');
//未定义
var num5;
call
console.log(toString.call(123)) //[object Number]
var num = 123;
console.log(num.toString()) //toString() 方法可把一个逻辑值转换为字符串,并返回结果
数据类型检测进阶
数据类型判断 - typeof
console.log(typeof undefined)//'undefined'
console.log(typeof null) // well-known bug
console.log(typeof true) //'boolean'
console.log(typeof 123) //'number'
console.log(typeof "abc") //'string'
console.log(typeof function() {}) //'function'
var arr=[];
console.log(typeof {}) //'object'
console.log(typeof arr)//'object'
console.log(typeof unknownVariable) //'undefined'
// 在使用 typeof 运算符时采用引用类型存储值会出现一个问题,
// 无论引用的是什么类型的对象,它都返回 "object"
数据类型判断 - toString.call
通用但很繁琐的方法: prototype
console.log(toString.call(123)) //[object Number]
console.log(toString.call('123')) //[object String]
console.log(toString.call(undefined)) //[object Undefined]
console.log(toString.call(true)) //[object Boolean]
console.log(toString.call({})) //[object Object]
console.log(toString.call([])) //[object Array]
console.log(toString.call(function(){})) //[object Function] console.log(Object.prototype.toString.call(str) === '[object String]') //-------> true;
console.log(Object.prototype.toString.call(num) === '[object Number]') //-------> true;
console.log(Object.prototype.toString.call(arr) === '[object Array]') //-------> true;
console.log(Object.prototype.toString.call(date) === '[object Date]') //-------> true;
console.log(Object.prototype.toString.call(fn) === '[object Function]') //-------> true;
数据类型判断 - instanceof
// 判断已知对象类型的方法: instanceof
console.log(arr instanceof Array) //---------------> true
console.log(date instanceof Date) //---------------> true
console.log(fn instanceof Function) //------------> true
//alert(f instanceof function) //------------> false
//注意:instanceof 后面一定要是对象类型,并且大小写不能错,该方法适合一些条件选择或分支。
数据类型判断 - 根据对象的constructor判断: constructor
// 根据对象的constructor判断: constructor
var arr=[];
console.log('数据类型判断 - constructor')
console.log(arr.constructor === Array) //----------> true
console.log(date.constructor === Date) //-----------> true
console.log(fn.constructor === Function) //-------> true
数据类型判断 函数封装
判断变量是不是数值型
function isNumber0(val){
return typeof val === 'number';
}
// 但有些情况就不行,比如:
// 1 var a;
// 2 alert(isNumber(parseInt(a)));
// 但实际上变量a是NaN,它是不能用于数值运算的。
// 所以上面的函数可以修改为:
function isNumber(val){
return typeof val === 'number' && isFinite(val);
}
// 顺便介绍一下JavaScript isFinite() 函数,isFinite() 函数用于检查其参数是否是无穷大,
// 如果 number 是有限数字(或可转换为有限数字),
// 那么返回 true。否则,如果 number 是 NaN(非数字),或者是正、负无穷大的数,则返回 false。
判断变量是不是布尔类型
function isBooleanType(val) {
return typeof val ==="boolean";
}
判断变量是不是字符串类型
function isStringType(val) {
return typeof val === "string";
}
判断变量是不是Undefined
function isUndefined(val) {
return typeof val === "undefined";
}
var a;//a是undefined
var s = "strType";
alert("变量a是Undefined的判断结果是:"+isUndefined(a));
alert("变量s是Undefined的判断结果是:"+isUndefined(s));
判断变量是不是对象
function isObj(str){
if(str === null || typeof str === 'undefined'){
return false;
}
return typeof str === 'object';
}
var a;
var b = null;
var c = "str";
var d = {};
var e = new Object();
alert("变量a是Object类型的判断结果是:"+isObj(a));//false
alert("变量b是Object类型的判断结果是:"+isObj(b));//false
alert("变量c是Object类型的判断结果是:"+isObj(c));//false
alert("变量d是Object类型的判断结果是:"+isObj(d));//true
alert("变量e是Object类型的判断结果是:"+isObj(e));//true
判断变量是不是null
function isNull(val){
return val === null;
}
/*测试变量*/
var a;
var b = null;
var c = "str";
//弹出运行结果
alert("变量a是null的判断结果是:"+isNull(a));//false
alert("变量b是null类型的判断结果是:"+isNull(b));//true
alert("变量c是null类型的判断结果是:"+isNull(c));//false
判断变量是不是数组
//数组类型不可用typeof来判断。因为当变量是数组类型是,typeof会返回object。
//方法1
function isArray1(arr) {
return Object.prototype.toString.call(arr) === '[object Array]';
}
//方法2
function isArray2(arr) {
if(arr === null || typeof arr === 'undefined'){
return false;
}
return arr.constructor === Array;
}
Jquery判断数据类型
// jQuery提供一系列工具方法,用来判断数据类型,以弥补JavaScript原生的typeof运算符的不足。
// 以下方法对参数进行判断,返回一个布尔值。 // jQuery.isArray():是否为数组。
// jQuery.isEmptyObject():是否为空对象(不含可枚举的属性)。
// jQuery.isFunction():是否为函数。
// jQuery.isNumeric():是否为数字。
// jQuery.isPlainObject():是否为使用“{}”或“new Object”生成的对象,而不是浏览器原生提供的对象。
// jQuery.isWindow():是否为window对象。
// jQuery.isXMLDoc():判断一个DOM节点是否处于XML文档之中。
原型对象的进阶
属性屏蔽理论
function Product() {
//属性
this.name = '神仙';
// 属性
this.description = ''
this.buy = function() {
alert('构造函数对象')
}
}
Product.prototype = {
name: '魔鬼',
buy: function() {
alert('原型对象')
}
}
var product = new Product()
console.log(product.name)
delete product.name
product.name = '魔鬼2'
console.log(product.name)
/*原型属性屏蔽理论 -- 乌云蔽日*/
console.log(product.buy())
/*清除乌云*/
delete product.buy
//console.log(product.name)
console.log(product.buy())
/*被屏蔽之后如何获取 */
//console.log(Product.prototype.buy())
hasOwnProperty
//hasOwnProperty : 看是不是对象自身下面的属性
function Product(){
this.name='iphone'
}
Product.prototype={
age:100
}
var iphone = new Product()
console.log(iphone.hasOwnProperty('name')) //true
console.log(iphone.hasOwnProperty('age')) //false,原型下面的属性
constructor
//constructor : 查看对象的构造函数
function Product(){
}
var iphone = new Product();
alert( iphone.constructor ); //Product
var arr = [];
alert( arr.constructor == Array ); //true
面相对象术语
原型构造函数
原型对象
1.原型对象里面的属性 -- 简称原型属性
Product.prototype.age = 12;
2.原型方法
Product.prototype.add=function(){}
//实例化 抽象 具体 实例 --- new Product ---类名
//使用的使用 需要先实例化:
var product = new Product(); //实例对象 实例
//如何访问对象里面的方法属性 -- 点语法
console.log(product.name)
product.add();
构造函数对象的属性和原型对象的属性区别
原型对象属性 原型对象方法 语法规范
//构造函数对象的属性和原型对象的属性
//构造函数对象属性不共享 原型对象属性共享
var iphone =new Product('iphone')
var android =new Product('android') //构造函数对象属性不共享
console.log(iphone.name) //iphone
console.log(android.name) //android //原型对象属性被所有实例共享
console.log(iphone.date) //2015/10/0
console.log(android.date) //2015/10/0
字面量
//简单字面量 - 描述现实世界
var book ={name:'盗墓笔记',price:100}
var product={name:'iphone4s',price:6000}
console.log(product.name)
//复杂字面量
var book = {
name : "盗墓笔记",
"main title" : "悬疑类小说",
//当属性名中间有空格,或者“-”时,要用引号 把 属性名括起来
author : {
//对象的属性也可以是对象
name : "徐磊",
nickname : "南派三叔",
works:[{name:'盗墓笔记',data:'2010'},{name:'大漠苍狼',data:'2011'},{name:'怒江之战',data:'2012'}]
}
};
console.log(book.name)
console.log(book['main title'])
console.log(book.author.name)
继承
前面讲过js中的面向对象其实是两个对象,一般构造函数对象中放置属性,原型对象中放置所有实例共享的方法
构造函数创建的实例为什么能访问原型对象的方法属性 -- 继承
构造函数对象
function Person(name, sex) {
this.name = name;
this.sex = sex;
}
// 定义Person的原型,原型中的属性可以被自定义对象引用
// 两个对象的本质关系:原型对象继承了构造函数对象,因而可以访问构造函数对象的一切方法,属性
Person.prototype = {
getName: function() {
return this.name;
},
getSex: function() {
return this.sex;
}
}
JS高级学习路线——面向对象进阶的更多相关文章
- JS高级---学习roadmap---5 parts
JS高级---学习roadmap---5 parts part 1-3 part 4-5
- JS高级学习历程-1
JS高级-34-昨天内容回顾 时间:2015-5-11 1.DOM获取元素节点 document.getElenmentById(id 属性值) ...
- Python学习之面向对象进阶
面向对象进阶当然是要谈谈面向对象的三大特性:封装.继承.多态 @property装饰器 python虽然不建议把属性和方法都设为私有的,但是完全暴露给外界也不好,这样,我们给属性赋值的有效性九无法保证 ...
- 转:JS高级学习笔记(8)- JavaScript执行上下文和执行栈
必看参考: 请移步:博客园 JavaScript的执行上下文 深入理解JavaScript执行上下文和执行栈 JavaScript 深入之执行上下文 写在开头 入坑前端已经 13 个月了,不能再称自己 ...
- js高级程序设计 笔记 --- 面向对象的程序设计
1,理解对象 通过对象字面量的方式,创建一个对象,为它添加属性和方法: var obj = { a: 1, b:2, sayA(){ console.log(this.a)}} 1,属性类型: 数据属 ...
- JS高级学习历程-15
昨天内容回顾 面向对象的私有成员.静态成员 私有成员:在构造函数里边定义局部变量,就是私有成员. 静态成员:在js里边,函数就是对象,可以通过给函数对象声明成员方式声明静态成员. 原型继承 关键字:p ...
- JS高级学习历程-14
昨天内容回顾 1. 面向对象的私有成员.静态成员 私有成员:在构造函数里边定义局部变量,就是私有成员. 静态成员:在js里边,函数就是对象,可以通过给函数对象声明成员方式声明静态成员. 2. 原型继承 ...
- JS高级学习历程-10
[面向对象] 面向对象的三大特性:封装.继承.多态 封装:在“类”里边有关键字public.protected.private 对成员进行声明,这样每个成员的访问都会受到不同关键字的限制. 继承:在p ...
- python学习总结(面向对象进阶)
-------------------类属性和实例属性关系------------------- 1.类属性和实例属性关系 1.实例属性 实例对象独有的属性 2.类属性 ...
随机推荐
- Git commit message和工作流规范
目的 统一团队Git commit日志标准,便于后续代码review,版本发布以及日志自动化生成等等. 统一团队的Git工作流,包括分支使用.tag规范.issue等 Git commit日志参考案例 ...
- ERP实施顾问工作中应努力做到哪些?
1.树立并分享信誉 准确的为自己定位,并积极树立自己的信誉.从这样两个角度去考虑问题,一是从高层管理者的角度去思考行业竞争和公司运作的问题,一是从专业.细致的角度去考虑单据.报表.界面等数据处理的问题 ...
- KoaHub平台基于Node.js开发的Koa 连接支付宝插件代码信息详情
KoaHub平台基于Node.js开发的Koa 链接支付宝插件代码信息详情 easy-alipay alipay payment & notification APIs easy-alipay ...
- MySQL查询语句的45道练习
一.设有一数据库,包括四个表:学生表(Student).课程表(Course).成绩表(Score)以及教师信息表(Teacher).四个表的结构分别如表1-1的表(一)~表(四) ...
- Android 实现QQ第三方登录
Android 实现QQ第三方登录 在项目中需要实现QQ第三方登录,经过一番努力算是写出来了,现在总结以下,以防以后遗忘,能帮到其他童鞋就更好了. 首先肯定是去下载SDK和DEMO http://wi ...
- php与mysql的常规使用
<?php header("Content-type:text/html;charset=GBK"); /* 通常,php网页中完成有关数据库的操作,首先,需要如下代码: $ ...
- "the hypervisor is not running" 故障
在我们日常服务器管理中,常常会遇到创建虚拟机,如果在一台新部署的 Hyper-V 上新建一个 Virtual Machine 时,出现错误信息:"The virtual machine co ...
- 解决Antimalware Service Executable CPU占用高听语音
windows8/8.1,WIN10自带的安全软件Windows defender还不错,基本可以不用装其他杀毒软件了. 但是其进程Antimalware Service Executable 出现C ...
- python常见的特异点
编码问题 Python中默认的编码格式是 ASCII 格式,在没修改编码格式时无法正确打印汉字,所以在读取中文时会报错.解决方法为只要在文件开头加入 # -*- coding: UTF-8 -*- 或 ...
- static成员是可以被其所在class创建的实例访问!!!
<span style="font-family: Arial, Helvetica, sans-serif; ">关于静态方法以及静态变量的使用就不详细的说了,我就这 ...