javascript 笔记

一、函数

1.命名函数表达式 标示符(这里是函数a)不能在外围的作用域内有效

var b = function a () {
    console.log(a) // function   
}
b()
console.log(a) //a is not defined

2.自执行函数,需要将函数作为function 表达式 而不是 函数声明。

(function a() {}()); 
(function a(){})();
!function a(){}();
-function a(){}();
1, function a(){}()

二、原型连

class B {}
class A extends B {}
let a  = new A()
let b = new B()
a.__proto__ === A.prototype
a.__proto__.__proto__ === B.prototype
a.__proto__.__proto__.__proto__ === Object.prototype
a.__proto__.__proto__.__proto__.__proto__ === null
A.__proto__ === B
A.__proto__.__proto__ === Function.prototype
A.__proto__.__proto__.__proto__ === Object.prototype
// 原生构造函数 
Object | String | Number | Function | Map |  Set.... .__proto__ === Function.prototype 

es5 实现类似es6 class 的继承(双链继承)

function A (val) {
  this.a = val
}
A.prototype.aSay = function() {
 console.log('a say', this.a)
}
function B (val) {
  this.b = val
}

B.prototype.bSay = function() {
 console.log('b say', this.b)
}

function extend(Child, Parent) {
  return function (val) {
     var c= new Child(val)
     Parent.call(c, val) // 将父类的属性赋值到child 
     var p= Object.getPrototypeOf(c)
     Object.setPrototypeOf(p, Parent.prototype) // 继承父类的方法 c.__proto__.__proto__ === Parent.prototype
    
     Object.setPrototypeOf(Child, Parent) // child.__proto__ === Parent 实现静态方法的继承

     return c 
  }
}
var  AB = extend(A, B) 
var ab = new AB(3)
ab.constructor === A

Number String 对象类型

var a = '1'
new Number(a) // 数字1 的对象形式
Number(a)  // 转换为数字
var a = 10
a.toString()
// 其实:
wrapper = new Number(a)
wrapper.toString()// "10"
delete wrapper

当获取一个数字的属性时,会先转换成对象形态再去获取属性(toString, valueOf),然后立马删除对象

var a = 1
a.test = 100
a.test // undefined
// 其实:
wrapper = new Number(a);
wrapper.test = 100;
delete wrapper;

当设置一个数字的属性时,也会先转换成对象形态设置属性,因此不会报错,但是设置完成后会立马删除此对象。因此设置的属性无法获取。

三、作用域链

activeExecutionContext = {
    VO: {...}, // or AO
    this: thisValue,
    Scope: [ // Scope chain
      // 所有变量对象的列表
      // for identifiers lookup
    ]
};

其中Scope ,为作用域链,function foo(){} 函数激活时 fooContext.Scope = fooContext.AO + foo.[[Scope]] (其中foo.[[Scope]]为创建时就存在)
with 能够修改作用域将其参数置为作用域的最前边 。 foo + AO|VO + [[Scope]]

obj = {a:1}
with(obj) {
   console.log(a) // 1
    var a= 2
   // 获取的实际是obj.a 。
}

console.log(obj.a) //2 

with(obj) {
 let a = 3
}
console.log(obj.a)  // 2

偏门题

function a() {
    alert(this); 
}
a.call(null);// window (当call null undefined时 设置为window)
a.call(1) // Number{1}
posted @ 2020-03-08 20:59  吃个石头  阅读(161)  评论(0编辑  收藏  举报