顺便宣传一下:Github来源: | 求星星 ✨ | 欢迎 star,鼓励一下作者。
希望能够帮助更多的小伙伴。加我?即可交流问题(不是大佬,互相学习,创造良好的学习环境)。以下哪些你不懂呢?
- 哪里不懂的,我们可以下方评论交流
扩展的对象功能
- 对象类别
命名一个函数为 createPerson()
,其作用创建了一个对象:
function createPerson(name, age) {
return {
name: name,
age: age
};
}
当对象的一个属性名称与本地变量名相同时,ES6:
function createPerson(name, age) {
return {
name,
age
},
}
es5写法:
var person = {
name: 'jeskson',
sayName: function() {
console.log(this.name);
}
};
es6写法:
var person = {
name: 'jeskson',
sayName() {
console.log(this.name);
}
};
- 需计算的属性名
示例:
var person = {},
lastName = "last name";
person["first name"] = "da1";
person[lastName] = "da2";
console.log(person["first name"]); // da1
console.log(person[lastName]); // da2
示例中两个属性名包含了空格,不能使用小数点表示法来引用它们,方括号表示法允许将任意字符串用作属性名。
示例优化:
var person = {
"first name": "jeskson"
};
console.log(person["first name"]); // jeskson
var lastName = "last name";
var person = {
"first name": "da1",
[lastName]: "da2"
};
console.log(person["first name"]); // "da1"
console.log(person[lastName]); // "da2"
示例:
var da = " name";
var pserson = {
["first + da ]: "da1",
["last" + da ]: "da2"
};
console.log(person["first name"]); // "da1"
console.log(person["last name"]); // "da2"
- 相等运算符
( == )
或严格相等运算符( === )
- ES6:
Object.is()
,返回true,要求二者类型相同并且值也相等
示例:
console.log(+0 == -0); // true
console.log(+0 === -0); // true
console.log(Object.is(+0, -0)); // false
console.log(NaN == NaN); // false
console.log(NaN === NaN); // false
console.log(Object.is(NaN, NaN)); // true
console.log(5 == 5); // true
console.log(5 == "5"); // true
console.log(5 === 5); // true
console.log(5 === "5"); // false
console.log(Object.is(5, 5)); // true
console.log(Object.is(5, "5")); // false
Object.assign()
方法
浅复制,当属性值为对象时,仅复制其引用
function mixin(receiver, supplier) {
Object.keys(supplier).forEach(function(key) {
receiver[key] = supplier[key];
});
return receiver;
}
Object.assign()
方法,该方法 接受一个接收者,以及任意数量的供应者,并会返回接收者。
示例:
"use strict";
var person = {
name: "da1",
name: "da2" // 在 ES6 严格模式中不会出错
};
console.log(person.name); // "da2"
Object.getPrototypeOf()
方法来从任意指定对象中获取其原型Object.setPrototypeOf()
方法修改任意指定对象的原型
示例:
let person = {
getGreeting() {
return "hello";
}
};
let dog = {
getGreeting() {
return "hai";
}
};
let friend = Object.create(person);
console.log(friend.getGreeting()); // "hello"
console.log(Object.getPrototypeOf(friend) === person); // true
Object.setPrototypeOf(friend, dog);
console.log(friend.getGreeting()); // "hai"
console.log(Object.getPrototypeOf(friend) === dog); // true
Object.getPrototypeOf()
方法确保了能调用正确的原型,并在其返回结果上附加了一个字符串。
示例:
let person = {
getGreeting() {
return "hello"
}
};
let dog = {
getGreeting() {
return "woof";
}
};
let friend = {
getGreeting() {
return Object.getPrototypeOf(this).getGreeting.call(this) + ", hi!";
}
};
Object.setPrototypeOf(friend, person);
console.log(friend.getGreeting()); // "hello hi!"
console.log(Object.getPrototypeOf(frined) === person); // true
Object.setPrototypeOf(friend,dog);
console.log(friend,getGreeting()); // "woof, hi!"
console.log(Object.getPrototypeOf(friend) === dog); // true
call(this)
,能确保正确设置原型方法内部的this
值
示例:
let friend = {
getGreeting() {
// Object.getPrototypeOf(this).getGreeting.call(this)
return super.getGreeting() + ", hi!";
}
}
使用ES6的super
,示例:
let person = {
getGreeting() {
return "hello";
}
};
let friend = {
getGreeting() {
return super.getGreeting() + ", hi!";
};
Object.setPrototypeOf(friend, person);
let relative = Object.create(friend);
console.log(person.getGreeting()); // "hello"
console.log(friend.getGreeting()); // "hello, hi!"
console.log(relative.getGreeting()); // "hello, hi!"
深入系列专题
1.JavaScript 深入之从原型到原型链
- JavaScript 深入之从原型到原型链
2.JavaScript 深入之词法作用域和动态作用域
- JavaScript 深入之词法作用域和动态作用域
3.JavaScript深入之执行上下文栈
- JavaScript深入之执行上下文栈
4.JavaScript深入之变量对象
- JavaScript深入之变量对象
5.JavaScript深入之作用域链
- JavaScript深入之作用域链
6.JavaScript 深入之从 ECMAScript 规范解读 this
- JavaScript 深入之从 ECMAScript 规范解读 this
7.JavaScript深入之执行上下文
- JavaScript深入之执行上下文
8.JavaScript深入之闭包
- JavaScript深入之闭包
9.JavaScript深入之参数按值传递
- JavaScript深入之参数按值传递
10.JavaScript深入之call和apply的模拟实现
- JavaScript深入之call和apply的模拟实现
11.JavaScript深入之bind的模拟实现
- JavaScript深入之bind的模拟实现
12.JavaScript深入之new的模拟实现
- JavaScript深入之new的模拟实现
13.JavaScript 深入之类数组对象与 arguments
- JavaScript 深入之类数组对象与 arguments
14.JavaScript深入之创建对象的多种方式以及优缺点
- JavaScript深入之创建对象的多种方式以及优缺点
- ES6 class语法
- 三要素
UML
类图- 初始化
npm
环境 - 安装
webpack
- 安装
webpack-dev-server
- 安装
babel
npm init
package.json
// package.json
// "dev": "wepack --config ./webpack.dev.config.js --mode development"
{
"name": "design-pattern-text",
"version": "1.0.0",
"description": "",
"main": "index.js",
"scripts": {
"test": "echo \"Error: no test specified\" && exit 1",
"dev": "webpack-dev-server --config ./webpack.dev.config.js --mode development"
},
"author": "",
"license": "ISC",
"devDependencies": {
"html-webpack-plugin": "",
"webpack": "",
"webpack-cli": "",
"webpack-dev-server": ""
}
}
npm install webpack webpack-cli --save-dev
webpack.dev.config.js
// webpack.dev.config.js
module.exports = {
entry: './src/index.js‘,
output: {
path: __dirname,
filename: './release/bundle.js'
}
}
npm run dev
npm install webpack-dev-server html-webpack-plugin --save-dev
// webpack.dev.config.js
const path = require('path')
const HtmlWebpackPlugin = require('html-webpack-plugin')
module.exports = {
entry: './src/index.js‘,
output: {
path: __dirname,
filename: './release/bundle.js'
},
module: {
rules: [{
test: /\.js?$/,
exclude: /(node_modules)/,
loader: 'babel-loader' // es6语法转es5语法
}]
},
glugins: [
new HtmlWebpackPlugin({
template: './index.html'
})
],
devServer: {
contentBase: path.jon(__dirname,'./release'), // 根目录
open: true, // 自动打开浏览器
port: 8080 // 端口
}
}
npm install babel-core babel-loader babel-polyfill babel-preset-es2015 babel-preset-latest --save-dev
// 根目录.babelrc
{
"presets": ["es2015", "latest"],
"plugins": []
}
- 概念
- 三要素:继承,封装,多态
- JS的应用举例
- 面向对象的意义
示例:
// 类
class People {
constructor(name,age) {
this.name = name
this.age = age
}
eat() {
alert(`${this.name} eat something`)
}
speak() {
alert(`My name is ${this.name}, age ${this.age}`)
}
}
// 对象(实例)
// 创建实例
let da1 = new Perople('jeskson1', 12)
da1.eat()
da1.speak()
// 创建实例
let da2 = new People('jeskson2', 13)
da2.eat()
da2.speak()
- 继承,子类继承父类
- 封装,数据的权限和保密
- 多态,同一接口不同实现
// 继承
class People {
constructor(name,age) {
this.name = name
this.age = age
}
eat() {
alert(`${this.name} eat something`)
}
speak() {
alert(`My name is ${this.name}, age ${this.age}`)
}
}
// 子类继承父类
class Student extends People {
constructor(name, age, number) {
super(name, age)
this.number = number
}
study() {
alert(`${this.name} study`)
}
}
// 实例
let jeskson1 = new Student('da1', 10, '01')
jeskson1.study()
console.log(jeskson1.number)
jeskson1.eat()
- 封装(
public
完全开发,protected
对子类开放,private
对自己开放) - 使用
typescript
// 封装 父类
class People {
public name
private age
protected weight
constructor(name, age) {
this.name = name
this.age = age
this.weight = 223
}
eat() {
alert(`${this.name} eat something`)
}
speak() {
alert(`My name is ${this.name}, age ${this.age}`)
}
}
// 子类
class Student extends People {
number
private grilfriend
constructor(name, age, number) {
super(name,age)
this.number = number
this.girlfriend = '小舞'
}
study() {}
getWeight() {}
}
- 多态:同一接口的不同表现
// 保持子类的开放性和灵活性
class People {
constructor(name) {
this.name = name
}
say() {}
}
class A extends People {
constructor(name) {
super(name)
}
say() {console.log('A dadaqianduan.cn')}
}
class B extends People {
constructor(name) {
super(name)
}
say() {console.log('B dadaqianduan.cn')}
}
let a = new A('a')
a.say()
let b = new b('b')
b.say()
- 面向对象:顺序,判断,循环,结构化
15.JavaScript深入之继承的多种方式和优缺点
- JavaScript深入之继承的多种方式和优缺点
JavaScript专题
1.JavaScript专题之跟着underscore学防抖
- JavaScript专题之跟着underscore学防抖
window 的 resize、scroll
mousedown、mousemove
keyup、keydown
2.JavaScript专题之跟着 underscore 学节流
- JavaScript专题之跟着 underscore 学节流
3.JavaScript专题之数组去重
- JavaScript专题之数组去重
4.JavaScript专题之类型判断(上)
- JavaScript专题之类型判断(上)
5.JavaScript专题之类型判断(下)
- JavaScript专题之类型判断(下)
Undefined、Null、Boolean、Number、String、Object
[object Number]
[object String]
[object Boolean]
[object Undefined]
[object Null]
[object Object]
[object Array]
[object Date]
[object Error]
[object RegExp]
[object Function]
[object Math]
[object JSON]
[object Arguments]
// jquery:
type: function(obj) {
if(obj == null) {
return obj + "";
}
return typeof obj === "object" || typeof obj === "function" ? class2type[toString.call(obj) ] || "object" : typeof obj;
}
6.JavaScript专题之深浅拷贝
-
JavaScript专题之深浅拷贝
-
浅拷贝:复制引用方法,两者都会发生变化
-
深拷贝:即使嵌套了对象,也相互分离,互不影响
var myObj = {...};
var myObj = new Object();
类型:对象是JavaScript的基础。6种主要类型:
string
number
boolean
null
undefined
object
函数就是对象的一个子类型,JavaScript中的函数是“一等公民”,因为它们本质上和普通的对象一样,所以可以像操作其他对象一样操作函数。
常见内置对象:
String
Number
Boolean
Object
Function
Array
Date
RegExp
Error
Object.assign(...)
方法的第一个参数是目标对象,之后还可以跟一个或多个源对象。它会遍历一个或多个源对象的所有可枚举的自有键并把它们复制到目标对象,最后返回目标对象
示例:
function anotherFunction() { /*..*/ }
var anotherObject = {
c: true
};
var anotherArray = [];
var myObject = {
a: 2,
b: anotherObject, // 引用,不是复本!
c: anotherArray, // 另一个引用!
d: anotherFunction
};
anotherArray.push( anotherObject, myObject );
var newObj = Object.assign( {}, myObject );
newObj.a; // 2
newObj.b === anotherObject; // true
newObj.c === anotherArray; // true
newObj.d === anotherFunction; // true
var myObject = {
a: 2
};
Object.getOwnPropertyDescriptor(myObject, "a");
// {
// value: 2,
// writable: true,
// enumerable: true,
// configurable: true,
// }
// writable可写
// enumerable可枚举
// configurable可配置
var myObject = {};
Object.defineProperty(myObject, "a", {
value: 2,
writable: true,
configurable: true,
enumerable: true
});
myObject.a; // 2
使用defineProperty(...)
给myObject
添加了一个普通的属性并显式指定了一些特性。
writable
决定是否可以修改属性的值
示例:
var myObject = {};
Object.defineProperty(myObject,"a",{
value: 2,
writable: false, // 不可写
configurable: true,
enumerable: true
});
myObject.a = 3;
myObject.a; // 2
configurable
,只要属性是可配置的,就可以使用defineProperty(...)
方法来修改属性描述符。
var myObject = {
a: 2
};
myObject.a = 3;
myObject.a; // 3
Object.defineProperty(myObject, "a", {
value: 4,
writable: true,
configurable: false, // 不可配置
enumerable: true
});
myObject.a; // 4
myObject.a = 5;
myObject.a; //5
Object.defineProperty(myObject, "a", {
value: 6,
wirtable: true,
configurable: true,
enumerable: true
}); // TypeError
enumerable
,控制的是属性是否会出现在对象的属性枚举中。
// 创建一个真正的常量属性,不可修改,重定义,删除
var myObject = {};
Object.defineProperty(myObject, "a", {
value: 1,
writable: false,
configurable: false
});
// 禁止扩展,使用Object.preventExtensions(...)
// 禁 止 一 个 对 象 添 加 新 属 性 并 且 保 留 已 有 属 性
var myObject = {
a: 2
};
Object.preventExtensions(myObject);
myObject.b = 3;
myObject.b; // undefined
-
密封:
Object.seal(...)
会创建一个“密封”的对象,这个方法实际上会在一个现有对象上调用Object.preventExtensions(...)
并把所有现有属性标记为configurable:false
(虽然可以 修改属性的值)。 -
冻结:
Object.freeze(..)
会创建一个冻结对象,这个方法实际上会在一个现有对象上调用Object.seal(..)
并把所有“数据访问”属性标记为writable:false
,这样就无法修改它们的值。
getter
是一个隐藏函数,会在获取属性值时调用setter
是一个隐藏 函数,会在设置属性值时调用
示例:
var myObject = {
a: 2
};
("a" in myObject); // true
("b" in myObject); // false
myObject.hasOwnProperty("a"); // true
myObject.hasOwnProperty("b"); // false
in
操作符会检查属性是否在对象及其[[Prototype]]
原型链中hasOwnProperty(...)
只会检查属性是否在myObject
对象中,不会检查[[Prototype]]
链
示例:
var myObject = {};
Object.defineProperty(
myObject,
"a",
{ enumerable: true, value: 2 }
);
Object.defineProperty(
myObject,
"b",
{ enumerable: false, value: 3}
);
myObject.b; // 3
("b" in myObject); // true
myObject.hasOwnProperty("b"); // true
for(var k in myObject) {
console.log(k, myObject[k]);
}
// "a" 2
检查属性是否可枚举:
var myObject = {};
Object.defineProperty(
myObject,
"a",
{enumerable: true, value: 2}
);
Object.defineProperty(
myObject,
"b",
{enumerable: false, value:3}
);
myObject.propertyIsEnumerable("a"); // true
myObject.propertyIsEnumerable("b"); // false
Object.keys(myObject); // ["a"]
Object.getOwnPeropertyNames(myObject); // ["a", "b"]
-
propertyIsEnumerable(...)
会检查给定的属性名是否直接存在于对象中,并满足enumerable: true
-
Object.keys(...)
会返回一个数组,包含所有可枚举属性 -
Object.getOwnPropertyNames(...)
会返回一个数组,包含所有属性,无论它们是否可枚举 -
in
和hasOwnProperty(...)
的区别在于是否查找[[Prototype]]
链 -
Object.keys(...)
和Object.getOwnPropertyNames(...)
都只会查找对象直接包含的属性
可以使用 Object.preventExtensions(..)、Object.seal(..) 和 Object.freeze(..)
来设置对象的不可变性级别。
ES6
方法:forEach()
,every()
,some()
forEach(...)
会遍历数组中的所有值并忽略回调函数的返回值every(...)
会一直运行直到回调函数返回falsesome(...)
会一直运行直到回调函数返回true
ES6
中新增加了一种用来遍历数组的for...of
循环语法:
示例:
var myArray = [1,2,3];
for(var v of myArray) {
console.log(v);
}
// 1
// 2
// 3
7.JavaScript 专题之从零实现 jQuery 的 extend
- JavaScript 专题之从零实现 jQuery 的 extend
8.JavaScript 专题之如何求数组的最大值和最小值
- JavaScript 专题之如何求数组的最大值和最小值
var arr = [ 2,34,5,8];
function max(prev, next) {
return Math.max(prev, next);
}
console.log(arr.reduce(max));
arr.sort(function(a,b){return a-b;});
console.log(arr[arr.length-1]);
var max = eval("Math.max(" + arr + ")");
Math.max.applly(null, arr);
Math.max(...arr);
9.JavaScript 专题之数组扁平化
- JavaScript 专题之数组扁平化
10.JavaScript专题之学underscore在数组中查找指定元素
- JavaScript专题之学underscore在数组中查找指定元素
11.JavaScript专题之jQuery通用遍历方法each的实现
- JavaScript专题之jQuery通用遍历方法each的实现
12.JavaScript 专题之如何判断两个对象相等
- JavaScript 专题之如何判断两个对象相等
构造函数,类的继承,混入
两种类型的混入:1,显式;2,隐式
示例:
function mixin( sourceObj, targetObj ) {
for (var key in sourceObj) {
// 只会在不存在的情况下复制
if(!(key in targetObj)) {
targetObj[key] = sourceObj[key];
}
}
return targetObj;
}
var Vehicle = {
engines: 1,
ignition: function() {
console.log("truing on my engine");
},
drive: function() {
this.ignition();
console.log("steering and moving forward!");
}
};
var Car = mixin(Vehicle, {
wheels: 4,
drive: function() {
Vehicle.drive.call(this); // 多态
console.log(
"Rolling on all" + this.wheels + "wheels"
};
}
});
显式混入模式的一种变体被称为“寄生继承”,它既是显式的又是隐式的。
示例:
function Vehicle() {
this.engines = 1;
}
Vehicle.prototype.ignition = function() {
console.log("turning on my engine");
};
Vehicle.prototype.drive = function() {
this.ignition();
console.log("steering and moving forward");
};
// 寄生类Car
function Car() {
var car = new Vehicle();
car.wheels = 4;
var vehDrive = car.drive;
// 重写
car.drive = function() {
vehDrive.call(this);
console.log("rolling on all" + this.wheels + "wheels");
return car;
}
myCar.drive();
示例:
var Something = {
cool: function() {
this.greeting = "hello world";
this.count = this.count ? this.count + 1 : 1;
}
};
Something.cool();
Something.greeting; / "hello world"
Something.count; // 1
var Another = {
cool: function() {
// 隐式把Something 混入Another
Something.cool.call(this);
}
};
Another.cool();
Another.greeting; // "hello world"
Another.count; // 1 (count不是共享状态)
W3C标准事件流
W3C标准事件流: 包含3个阶段,捕获阶段,目标阶段,冒泡阶段。
- 在捕获阶段,事件对象通过目标的祖先从窗口传播到目标的父级。
- 在目标阶段,事件对象到达事件对象的事件目标。
- 在冒泡阶段,事件对象以相反的顺序通过目标的祖先传播,从目标的父级开始,到窗口结束。
- 先从顶层对象
window
开始一路向下捕获,直到达到目标元素,其后进入目标阶段。 - 目标元素 div 接收到事件后开始冒泡到顶层对象
window
。 - 单击了
<div>
元素,则首先会进行事件捕获,此时事件按window→document→<html>→<body>
的顺序进行传播 - 当事件对象传到
<div>
时进入目标阶段,接着事件对象又从目标对象传到body
,从而进入事件的冒泡阶段 - 事件对象按
<body>→<html>→document→window
的顺序传播事件。
13.JavaScript 专题之函数柯里化
- JavaScript 专题之函数柯里化
14.JavaScript 专题之惰性函数
- JavaScript 专题之惰性函数
15.JavaScript专题之函数组合
- JavaScript专题之函数组合
16.JavaScript 专题之函数记忆
- JavaScript 专题之函数记忆
17.JavaScript专题之递归
- JavaScript专题之递归
18.JavaScript专题之乱序
- JavaScript专题之乱序
19.JavaScript专题之解读 v8 排序源码
- JavaScript专题之解读 v8 排序源码
JavaScript中的对象有一个特殊的[[Prototype]]
内置属性,其实就是对于其他对象的引用。几乎所有的对象在创建时[[Prototype]]
属性都会被赋予一个非空的值。
- 使用
in
操作符来检查属性在对象中是否存在时,同样会查找对象的整条原型链。
示例:
var anotherObject = {
a: 2
};
// 创建一个关联到anotherObject的对象
var myObject = Object.create(anthorObject);
for(var k in myObject) {
console.log("found:" + k);
}
// found:a
("a" in myObject); // true
所有普通的 [[Prototype]]
链最终都会指向内置的 Object.prototype
所有的函数默认都会拥有一个名为 prototype
的公有并且不可枚举的属性,它会指向另一个对象
function Foo() {
// ...
}
Foo.prototype; // { }
var a = new Foo();
Object.getPrototypeOf( a ) === Foo.prototype; // true
new Foo()
会生成一个新对象,这个新对象的内部链接 [[Prototype]]
关联 的是 Foo.prototype
对象
Object.create(...)
会创建一个新对象并把它关联到我们指定的对象,Object.create(null)
会创建一个拥有空链接的对象,这个对象无法进行委托。
由于这个对象没有原型链,所以instanceof
操作符无法进行判断,因此总是会返回false。这些特殊的空[[Prototype]]
对象通常被称为“字典”,它们完全不会受到原型链的干扰,非常适合用来存储数据。
示例:
// polyfill 代码
if(!Object.create) {
Object.create = function(o) {
function F(){}
F.prototype = o;
return new F(); // 构造一个新对象进行关联
};
}
示例:
var anotherObject = {
a: 2
};
var myObject = Object.create( anotherObject, {
b: {
enumerable: false,
writable: true,
configurable: false,
value: 3
},
c: {
enumerable: true,
writable: false,
configurable: false,
value: 4
}
});
myObject.hasOwnProperty( "a" ); // false
myObject.hasOwnProperty( "b" ); // true
myObject.hasOwnProperty( "c" ); // true
myObject.a; // 2
myObject.b; // 3
myObject.c; // 4
示例:
var anotherObject = {
cool: function() {
console.log("cool");
}
};
var myObject = Object.create(anotherObject);
myObject.doCool = function() {
this.cool(); // 内部委托
};
myObject.doCool(); // "cool"
对象之间是通过内部的[[Prototype]]
链关联的。
示例:
class Task {
id;
// 构造函数Task()
Task(ID) { id = ID; }
outputTask() {output(id); }
}
class XYZ inherits Task {
label;
// 构造函数 XYZ()
XYZ(ID,Label) { super( ID ); label = Label; }
outputTask() { super(); output( label ); }
}
class ABC inherits Task {
// ...
}
推荐代码:
Task = {
setID: function(ID) { this.id = ID; },
outputID: function() { console.log( this.id ); }
};
// 让 XYZ 委托 Task
XYZ = Object.create( Task );
XYZ.prepareTask = function(ID,Label) {
this.setID( ID );
this.label = Label;
};
XYZ.outputTaskDetails = function() {
this.outputID(); console.log( this.label );
};
// ABC = Object.create( Task );
面向对象:
function Foo(who) {
this.me = who;
}
Foo.prototype.identify = function() {
return "I am " + this.me;
};
function Bar(who) {
Foo.call( this, who );
}
Bar.prototype = Object.create( Foo.prototype );
Bar.prototype.speak = function() {
alert( "Hello, " + this.identify() + "." );
};
var b1 = new Bar( "b1" );
var b2 = new Bar( "b2" );
b1.speak();
b2.speak();
对象关联:
Foo = {
init: function(who) {
this.me = who;
},
identify: function() {
return "I am " + this.me;
}
};
Bar = Object.create( Foo );
Bar.speak = function() {
alert( "Hello, " + this.identify() + "." );
};
var b1 = Object.create( Bar );
b1.init( "b1" );
var b2 = Object.create( Bar );
b2.init( "b2" );
b1.speak();
b2.speak();
示例:
// 父类
function Controller() {
this.errors = [];
}
Controller.ptototype.showDialog(title,msg) {
// 给用户显示标题和消息
};
Controller.prototype.success = function(msg) {
this.showDialog("Success", msg);
};
Controller.prototype.failure = function(err) {
this.errors.push(err);
this.showDialog("Error", err);
};
// 子类
function LoginController() {
Controller.call(this);
}
// 把子类关联到父类
LoginController.prototype = Object.create(Controller.prototype);
LoginController.prototype.getUser = function() {
return document.getElementById("login_username").value;
};
LoginController.prototype.getPassword = function() {
return docuemnt.getElementById("login_password").value;
};
LoginController.prototype.validateEntry = function(user, pw) {
user = user || this.getUser();
pw = pw || this.getPassword();
if( !(user && pw) ) {
return this.failure(
"please enter a username & password!"
);
}
else if( user.length<5) {
return this.failuer(
"password must be 5+ characters"
);
}
// 如果执行到这里表示通过验证
return true;
};
// 重写failure()
LoginController.prototype.failure = function(err) {
// "super" 调用
Controller.prototype.failure.call(
this,
"Login invalid" + err
);
};
// 子类
function AuthController(login) {
Controller.call(this);
// 合成
this.login = login;
}
// 把子类关联到父类
AuthController.prototype =
Object.crate(Controller.prototype);
AuthController.prototype.server = function(url, data) {
return $.ajax({
url: url,
data: data
});
};
AuthController.prototype.checkAuth = function() {
var user = this.login.getUser();
var pw = this.login.getPassword();
if (this.login.validateEntry(user.pw)) {
this.server( "/check-auth",{
user: user,
pw: pw
} ) .then( this.success.bind( this ) )
.fail( this.failure.bind( this ) );
}
};
// 重写基础的 success()
AuthController.prototype.success = function() {
//“super”调用
Controller.prototype.success.call( this, "Authenticated!" );
};
// 重写基础的 failure()
AuthController.prototype.failure = function(err) {
//“super”调用
Controller.prototype.failure.call(
this,
"Auth Failed: " + err
);
};
var auth = new AuthController();
auth.checkAuth(
// 除了继承,我们还需要合成
new LoginController()
);
对象关联:
var LoginController = {
errors: [],
getUser: function() {
return document.getElementById( "login_username" ).value;
},
getPassword: function() {
return document.getElementById( "login_password" ).value;
},
validateEntry: function(user,pw) {
user = user || this.getUser();
pw = pw || this.getPassword();
if (!(user && pw)) {
return this.failure( "Please enter a username & password!" );
}
else if (user.length < 5) {
return this.failure( "Password must be 5+ characters!" );
}
// 如果执行到这里说明通过验证
return true;
},
showDialog: function(title,msg) {
// 给用户显示标题和消息
},
failure: function(err) {
this.errors.push( err );
this.showDialog( "Error", "Login invalid: " + err );
}
};
// 让 AuthController 委托 LoginController
var AuthController = Object.create( LoginController );
AuthController.errors = [];
AuthController.checkAuth = function() {
var user = this.getUser();
var pw = this.getPassword();
if (this.validateEntry( user, pw )) {
this.server( "/check-auth",{
user: user,
pw: pw
} ) .then( this.accepted.bind( this ) )
.fail( this.rejected.bind( this ) );
}
};
AuthController.server = function(url,data) {
return $.ajax( {
url: url,
data: data
} );
};
AuthController.accepted = function() {
this.showDialog( "Success", "Authenticated!" )
};
AuthController.rejected = function(err) {
this.failure( "Auth Failed: " + err );
};
示例:
class Foo { methodName() { /* .. */ } }
个人专题
?力扣 (LeetCode)题目
- 两数之和,有效的括号,两数相加
- 合并两个有序链表,删除排序数组中的重复项,JavaScript笔记
- 力扣 (LeetCode)-最大子序和,JavaScript数据结构与算法(数组)
- 力扣 (LeetCode)-栈,括号生成 |刷题打卡
- 力扣 (LeetCode)-加一,队列 |刷题打卡
- 力扣 (LeetCode)-合并两个有序数组,字典,散列表|刷题打卡
- 力扣 (LeetCode)-对称二叉树,树|刷题打卡
- 力扣 (LeetCode)-104. 二叉树的最大深度,图|刷题打卡
- 排序,搜索,算法模式,算法复杂度 | 数据结构与算法综合笔记
- 力扣 (LeetCode)-28. 实现 strStr()
- 力扣 (LeetCode)-14. 最长公共前缀
- 力扣 (LeetCode)-13. 罗马数字转整数
?掘金文章
- 前端日常总结
- 一份不可多得的TypeScript系统入门整理
- JS葵花宝典秘籍笔记,为你保驾护航金三银四
- TypeScript趁早学习提高职场竞争力
- 前端模拟面试字数过23477万内容
- JavaScript数据结构之链表 | 技术点评
- JavaScript的数据结构-集合 |技术点评
- 这是我的第一次JavaScript初级技巧
- 一个合格的初级前端工程师需要掌握的模块笔记
- 【初级】个人分享Vue前端开发教程笔记
- localStorage和sessionStorage本地存储
- HTML5中的拖放功能
- 挑战前端知识点HTTP/ECMAScript
- 前端170面试题+答案学习整理(良心制作)
- 必学必会-音频和视频
- 前端HTML5面试官和应试者一问一答
- Vue.js笔试题解决业务中常见问题
- 前端面试必备ES6全方位总结
- 考前复习必备MySQL数据库(关系型数据库管理系统)
- 长篇总结之JavaScript,巩固前端基础
- 学习总结之HTML5剑指前端(建议收藏,图文并茂)
- 前端必学必会-多媒体-本地存储-浏览器与服务器的交互-通信功能
- 【建议?】记录一次BAT一线互联网公司前端JavaScript面试
- Web页面制作基础
- 【思维导图】前端开发-巩固你的JavaScript知识体系
- 【图文并茂,点赞收藏哦!】重学巩固你的Vuejs知识体系
- 【高能笔记】如何获得令人心动的前端offer | 掘金技术征文
- 11期前端冲刺必备指南-执行上下文/作用域链/闭包/一等公民
- 12期前端冲刺必备指南-HTTP/HTTPS/HTTP2/DNS/TCP/经典题
- 13期前端冲刺必备指南-this/call/apply/bind(万字长文)
- 14期-连肝7个晚上,总结了计算机网络的知识点!(共66条)
- 熬夜总结了 “HTML5画布” 的知识点(共10条)
- 16期-熬夜7天,我总结了JavaScript与ES的25个重要知识点!
- 17期-什么是MySQL数据库?看这一篇干货文章就够了!
- 18期-后端逆袭,一份不可多得的php学习指南
- 19期-当你在百度搜索关键字的时候,哪个网站会排在最前面?今天给大家科普一下“网站SEO”
- 前端学习总结,经验分享,项目经验分享过程 | 掘金技术征文-双节特别篇
- 写给前端程序员的英文学习指南 | 掘金技术征文-双节特别篇
- 【图文并茂,点赞收藏哦!】重学巩固你的Vuejs知识体系(上)
- 【图文并茂,点赞收藏哦!】重学巩固你的Vuejs知识体系(下)
- 【思维导图】前端开发JavaScript-巩固你的JavaScript知识体系
- (一)熟练HTML5+CSS3,每天复习一遍
- 面试官一上来就问我Chrome底层原理和HTTP协议(万字长文)
- 2020 年「我与技术面试那些事儿」| 掘金年度征文
- 【进阶】面试官问我Chrome浏览器的渲染原理(6000字长文)| 掘金年度征文
- 2020年小程序开发-云开发技术总结 | 掘金年度征文
- 腾讯位置服务开发应用 | 创作者训练营
- 达达前端个人web分享92道JavaScript面试题附加回答 | 创作者训练营
- 【这一年收到的书籍,感谢赠予!】一起回顾 2020,展望 2021 | 掘金年度征文
- 哪吒闹海,席卷图文学习前端Flex布局-七日打卡
- 针对CSS说一说|技术点评
- 原来也没有那么难!Vue商城开发 | 技术点评
❤️关注+点赞+收藏+评论+转发❤️
点赞、收藏和评论
我是Jeskson
(达达前端),感谢各位人才的:点赞、收藏和评论,我们下期见!(如本文内容有地方讲解有误,欢迎指出☞谢谢,一起学习了)
我们下期见!
- 技术创作者们,快来这里交作业啦 | 创作者训练营第二期
常见问题FAQ
- 免费下载或者VIP会员专享资源能否直接商用?
- 本站所有资源版权均属于原作者所有,这里所提供资源均只能用于参考学习用,请勿直接商用。若由于商用引起版权纠纷,一切责任均由使用者承担。更多说明请参考 VIP介绍。
- 提示下载完但解压或打开不了?
- 找不到素材资源介绍文章里的示例图片?
- 模板不会安装或需要功能定制以及二次开发?
发表评论
还没有评论,快来抢沙发吧!