Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

JS权威指南读书笔记-4章 #1

Open
hanyuxinting opened this issue Feb 10, 2017 · 0 comments
Open

JS权威指南读书笔记-4章 #1

hanyuxinting opened this issue Feb 10, 2017 · 0 comments

Comments

@hanyuxinting
Copy link
Owner

hanyuxinting commented Feb 10, 2017

1. 原始表达式-primary expression

表达式的原子级别。最小。常量/直接量、关键字、变量。
常量/直接量:1.23、'hello'、/pattern/----back to part3\10
关键字/js的一些保留字:true false null this
变量:i、sum、 undefined 当变量不存在时,表达式运算结果为undefined

2. 对象和数组的初始化表达式-对象直接量\数组直接量-新创建的对象和数组

不同于布尔直接量,非原始表达式,含有子表达式。
数组初始化表达式:[]、[1+2, 3+4]、[[1,2,3].[2,3,4]]、
[1,,,,,5] 这种中间空位会被填充为 undefined。

对象表达式:

3. 函数定义表达式-函数直接量-function

定义一个js函数。
以下代码中可以区别函数直接量和函数。
函数后不用加; 而函数直接量需要加;区分是声明变量结束。

4. 属性访问表达式-得到一个对象属性、或数组元素的值。(第六章)

. 运算和[]运算
先计算.[]运算符前的表达式,若为null或undefined,则抛出异常。so,经常用obj&&obj.x
这种语句判断。属性不存在,则返回undefined。
点运算符只适用要访问的属性名称是合法的标识符,且需要知道要访问的属性名。
用$.each可以遍历属性。
若属性名为保留字或包含空格和标点或是数字(数组而言),须使用方括号。
属性名是运算得出的值而不是固定值时,须用方括号。
对象属性:

数组属性:

5. 调用表达式-调用函数或方法。(第八章)

若函数使用return语句,则这个返回值为整个调用表达式的值。否则为undefined。
方法调用是针对一个对象里的方法而言。其实最终都是函数了~~(第九章)
普通函数调用,通常使用全局对象作为this的值,ES5严格模式下,this值为undefined。
了解严格模式 5.7.3

6. 对象创建表达式-创建一个对象并调用构造函数初始化新对象的属性。

new Object()/new Object
new Point(1,2)/new Point(1,2)

7. 运算符概述-关键字运算符、标点运算符。

delete
instanceof

delete 删除属性

x = 42;        // 隐式声明的全局变量
var y = 43;    // 显式声明的全局变量
myobj = {
  h: 4,    
  k: 5
}    

// 隐式声明的全局变量可以被删除
delete x;       // 返回 true 

// 显式声明的全局变量不能被删除,该属性不可配置(not configurable)
delete y;       // 返回 false 

//内置对象的内置属性不能被删除
delete Math.PI; // 返回 false

//用户定义的属性可以被删除
delete myobj.h; // 返回 true 

// myobj 是全局对象的属性,而不是变量
//因此可以被删除
delete myobj;   // 返回 true

function f() {
  var z = 44;

  // delete doesn't affect local variable names
  delete z;     // returns false
}

// Numbers
typeof 37 === 'number';
typeof 3.14 === 'number';
typeof Math.LN2 === 'number';
typeof Infinity === 'number';
typeof NaN === 'number'; // 尽管NaN是"Not-A-Number"的缩写
typeof Number(1) === 'number'; // 但不要使用这种形式!

// Strings
typeof "" === 'string';
typeof "bla" === 'string';
typeof (typeof 1) === 'string'; // typeof总是返回一个字符串
typeof String("abc") === 'string'; // 但不要使用这种形式!

// Booleans
typeof true === 'boolean';
typeof false === 'boolean';
typeof Boolean(true) === 'boolean'; // 但不要使用这种形式!

// Symbols
typeof Symbol() === 'symbol';
typeof Symbol('foo') === 'symbol';
typeof Symbol.iterator === 'symbol';

// Undefined
typeof undefined === 'undefined';
typeof declaredButUndefinedVariable === 'undefined';
typeof undeclaredVariable === 'undefined'; 

// Objects
typeof {a:1} === 'object';

// 使用Array.isArray 或者 Object.prototype.toString.call
// 区分数组,普通对象
typeof [1, 2, 4] === 'object';

typeof new Date() === 'object';

// 下面的容易令人迷惑,不要使用!
typeof new Boolean(true) === 'object';
typeof new Number(1) ==== 'object';
typeof new String("abc") === 'object';

// 函数
typeof function(){} === 'function';
typeof Math.sin === 'function';

// 定义构造函数
function C(){} 
function D(){} 

var o = new C();

// true,因为 Object.getPrototypeOf(o) === C.prototype
o instanceof C; 

// false,因为 D.prototype不在o的原型链上
o instanceof D; 

o instanceof Object; // true,因为Object.prototype.isPrototypeOf(o)返回true
C.prototype instanceof Object // true,同上

C.prototype = {};
var o2 = new C();

o2 instanceof C; // true

o instanceof C; // false,C.prototype指向了一个空对象,这个空对象不在o的原型链上.

D.prototype = new C(); // 继承
var o3 = new D();
o3 instanceof D; // true
o3 instanceof C; // true


// 数组
var trees = new Array("redwood", "bay", "cedar", "oak", "maple");
0 in trees        // 返回true
3 in trees        // 返回true
6 in trees        // 返回false
"bay" in trees    // 返回false (必须使用索引号,而不是数组元素的值)
"length" in trees // 返回true (length是一个数组属性)

// 内置对象
"PI" in Math          // 返回true

// 自定义对象
var mycar = {make: "Honda", model: "Accord", year: 1998};
"make" in mycar  // 返回true
"model" in mycar // 返回true

var color1 = new String("green");
"length" in color1 // 返回true
var color2 = "coral";
"length" in color2 // 报错(color2不是对象)

var mycar = {make: "Honda", model: "Accord", year: 1998};
delete mycar.make;
"make" in mycar;  // 返回false

var trees = new Array("redwood", "bay", "cedar", "oak", "maple");
delete trees[3];
3 in trees; // 返回false

当你删除一个数组元素时,数组的 length 属性并不会变小。

8. 算术表达式

  • 优先考虑字符串连接,然后才是加法运算。

9.关系表达式

相等和不等运算符

== 可以允许类型转化。
=== 则不允许类型转化。

1==='1'
false
1=='1'
true
null == null
true
null === null
true
undefined === undefined
true

null == undefined
true
null === undefined
false

true === true
true
null == null
true
false === false
true
NaN === NaN  // NaN 跟谁都不等,所以 x !== x ,
false
NaN == NaN
false
0 === -0
true
1 === -1
false

'北京' === '北京'
true
'\u2012' == '\u2012'
true
'北京' == '北京'
false
'北京'.localeCompare('北京')
0
'北京'.localeCompare('北京')
1

var s = new String('test'); s == 'test'
true
s === 'test'
false
s.valueOf() === s.toString()
true

'1' == true
true
'2' == true
false

NaN 跟谁都不等,所以 x !== x ,可以用来判断x是不是NaN~~

比较运算符

<
>
<=
>=

一般用于数字和字符串。

加号运算符和比较运算符的区别,加号以字符串优先,比较则以数字为优先。
1+2
3
1 + '2'
"12"
11>3
true
'11'>'3'
false
'11'>3
true
'one'>3 // 'one' -> NaN,NaN和任何比较都是false。
false

in 运算符

var point = {x: 1, y: 2};

point
Objectx: 1y: 2__proto__: Object__defineGetter__: __defineGetter__()__defineSetter__: __defineSetter__()__lookupGetter__: __lookupGetter__()__lookupSetter__: __lookupSetter__()constructor: Object()hasOwnProperty: hasOwnProperty()isPrototypeOf: isPrototypeOf()propertyIsEnumerable: propertyIsEnumerable()toLocaleString: toLocaleString()toString: toString()valueOf: valueOf()get __proto__: __proto__()set __proto__: __proto__()

'valueOf' in point
true
'__proto__' in point
true
'x' in point
true
'z' in point
false
var array = [4,5,6]; 4 in array
false
'4' in array
false

0 in array
true
'0' in array
true

instanceof 实例运算符

所有的对象都是Object的实例。
理解原型链~

var d = new String('test');
d instanceof String
true
d instanceof Date
false
d instanceof Object
true

10. 逻辑表达式

&&
||
!

以下等价:

if(a==b) do();
(a == b) && do();

11. 赋值表达式

= 给变量或属性赋值。
优先级很低的~

12. 表达式计算

eval

解释运行由 JS 源码组成的字符串,并返回值。
尽量不要用。

eval() 的问题:动态执行代码。
解释器不能提前优化。
当eval被赋值给其他变量时,调用该变量的方法很难优化。

eval() 传参字符串,并对该字符串当成JS代码进行编译(parse),编译成功后就执行该段代码。失败则抛出异常。

eval() 解析后的代码,如果有变量和eval外的代码相同,eval会使用该变量,甚至有可能改变该变量的值。
即,eval会改变它所在环境下的变量,如果很不幸这个eval在最顶层处调用,则会影响全局函数和全局变量。。

当其他代码来影响你的代码时,你的代码将会变得多么不可控~~~

// ##### 全局eval #####,不能修改局部变量和函数~
var g = eval; var x = 'gloval'; var y = 'global'; 
function f(){var x='local'; eval('x += "changed";'); return x;}
function gll(){var y='ll'; g('y += "changed";'); return y;}
console.log(f(), x);
localchanged gloval
console.log(gll(), y)
 ll globalchanged
console.log(y)
globalchanged
console.log(gll())
VM2113:1 ll
严格eval

私有上下文环境的局部eval~ 严格模式下,可以查询或更改局部变量,不能在局部作用域中定义新的变量或函数。
更像一个运算符~

但是,能不用就不要用了~~

13. 其他运算符

条件运算符~

?: 三目运算~

typeof运算符

两种写法~

x = null
typeof x
"object"
typeof(x)
"object"

void 运算符

一般用于 url中。

<a href="javascript:void(0);">我不跳转我就不跳转~</a>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

1 participant