目录
JS:... 1
ES:... 2
V8:... 2
nodejs:... 3
语法:... 4
注释:... 4
常量和变量:... 4
数据类型:... 6
类型转换:... 6
String字符串:... 8
Number数值型:... 10
运算符:... 11
表达式:... 17
https://developer.mozilla.org #提供完善的HTML、CSS、JS等技术资料
https://developer.mozilla.org/zh-CN/docs/Web/JavaScript #javascript指南
javascript,是一种动态的弱类型脚本解释语言,和HTML、CSS并称三大web前端核心技术,得到了几乎主流browser的支持;
94年,netscape公司成立并发布了netscape navigator浏览器,占据了很大的市场份额,网景意识到web需要动态,需要一种技术实现;
95年9月网景浏览器2发布测试版本livescript,随即在12月测试版本更名为javascript;同时期,ms推出IE并支持jscript、vbscript;
97年,netscape、ms、sun、borland(delphi、java工具、IDE工具)和其它组织确定了ECMAScript标准,js是ECMAScript标准的实现之一;
由于IE的捆绑销售行为,网景的单一浏览器市场萎缩,从90年代的90%下降至06年的1%;
99年网景被AOL收购,不久,netscape公开了浏览器代码,并创建了mozilla组织,mozilla组织使用gecko引擎重写浏览器,mozilla组织用gecko引擎发布了firefox浏览器;
03年5月,网景被解散;
AOL于07年12月宣布停止支持netscape浏览器;
netscape技术:
HTTP cookie,解决HTPP无状态;
javascript;
ssl协议;
jar格式文件,将java的class文件打包压缩,并加上签名;
12年4月9日,ms以10亿5千6百万购买800+项专利或专利授权;
ECMAScript,由ECMA国际(前身为欧洲计算机制造商协会,European Computer Manufacturers Association)通过ECMA-262标准化的脚本程序设计语言,该语言被广泛的应用于互联网;
javascript是商品名,目前商标权在oracle公司手中,ES是标准名;
根据ES标准,有很多实现引擎,包括javascript、jscript,它们都是ECMA-262标准的实现和扩展;
为什么browser兼容是个大问题?
html、css、js技术都在发展,标准版本很多,b内嵌的引擎实现不太一致,甚至有不按标准实现、或减少实现、或改变实现、或增加功能的实现,如IE就导致了开发人员负担,很难做到一套代码可兼容的跑在多b中,甚至不能跑在同一种b的不同版本中;
97年,制定首个ECMA-262版本;
99年12月,ES3,支持更强大的IE;
ES4太激进,最终放弃;
09年,ES5发布,得到广泛支持,支持严格模式,支持json;
15年,ES6发布,引入非常多的新的语言特性,还兼容旧版本特性,ES6之前按版本号命名,从ES6开始使用年份作为版本号,ES6即ECMAScript 2015;
在IE浏览器市场一家独大时,firefox、chrome异军突起;
09年9月2日,google的chrome浏览器发布,一并发布js引擎,即v8引擎,v8使用BSD协议开源;
v8引擎用C++开发,将javascript编译成了机器码,而不是字节码,还用很多优化方法提高性能,因此v8引擎速度非常快;
v8引擎还可独立运行,可嵌入到其它任何C++程序中;
v8引擎的诞生,使得服务器端运行js成为了方便的事情;
是服务器端运行javascript的开源、跨平台运行环境;
nodejs的原始作者ryan dahl,于09年发布,使用了v8引擎,并采用事件驱动、非阻塞异步IO模型;
10年,npm软件包管理诞生,通过它可方便的发布、分享nodejs的库和源代码;
nodejs4.0引入了ES6的语言特性;
当前学习js,就让它运行在最新版的nodejs上,为调度方便,也为使用最新的ES2017特性;
https://code.visualstudio.com/ # ms的visualstudio有自动完成功能,还可安装Node Exec插件,将js运行在nodejs上,F8运行脚本文件,F9停止
https://npm.taobao.org/mirrors/node
node-v10.11.0-linux-x64.tar.gz
node-v10.11.0-x64.msi #如果安装失败,禁用掉node运行环境中的performance counters 和ETW,全局安装目录D:\Program Files\nodejs,用户目录C:\Users\Administrator\AppData\Roaming\npm\
打开visualstudio,左侧Extension,搜索并安装Node Exec
vs code中快速生成html文件:
ctrl + N;右下角选择HTML;文件第一行输入!,回车;
1、单行注释:
//
2、多行注释:
/*
……
*/
3、/**回车之后每一行会自动加上*,c++开始就有
标识符:
必须是字母、数字、下划线、$符号;
且必须是字母、数字、下划线、$开头,依然是不能数字开头;
区分大小写;
声明:
var,声明一个变量;var会把变量作用域提升;
let,声明一个块作用域中的局部变量;
const,声明一个常量;
js中,变量声明和初始化是可以分开的;
常量和变量选择(C、C++都是这样):
如果明确知道一个标识符定义后不再修改,应尽量用const声明为常量,减少被修改的风险,减少bug;
例,错误示例:
console.log(a); //X,要往后写,在var a;之后
var a;
var b;
console.log(c) //X,c is not defined
输出:
undefined
Error:
e:\git_practice\js\node_20697e6bb6d28.tmp:17
console.log(c)
^
ReferenceError: c is not defined
例:
a = 'test'; //隐式声明带初始化,不推荐用,在严格模式下会产生异常,在赋值之前不能引用,因为它没有声明,一旦赋值就是全局作用域
var b; //只是声明,b为undefined
let c = 123; //规范的声明并初始化,声明全局或局部变量
var d = 456; //用var声明并初始化,不推荐,推荐用let
console.log(a,b,c,d)
输出:
test undefined 123 456
// const e; //X,SyntaxError: Missing initializer in const declaration
// e = 400;
// x = 6; //X,不规范的初始化,全局作用域,不推荐
const e = 400; //常量必须在声明时初始化,之后不能再改
console.log(e)
输出:
400
例:
function hello() {
var a = 100;
b = 200;
};
console.log(a) //X,作用域在函数内,突破不了
console.log(b)
例:
// console.log(a);
// var a = 100;
//相当于
var a; //提升的作用域,实际是把声明提前了
console.log(a);
a = 100;
输出:
undefined
// console.log(a); //X
// let a = 100;
let a;
console.log(a);
a = 100;
输出:
undefined
number,数值型,包括整型和浮点型;
boolean,布尔型,true和flase;
string,字符串;
null,只有一个值null;
undefined,变量声明未赋值的,对象未定义的属性;
object,是以上基本类型的复合类型,是容器;
symbol,ES6新引入类型;
NaN,not a number;
弱类型,不需要强制类型转换;
遇到字符串,加号就是拼接字符串,所有非字符串隐式转换为字符串;
如果没有字符串,加号把其它所有类型都当数字处理,非数字类型隐式转换为数字,undefined特殊为NaN;
如果是逻辑运算符、短路符,返回就是短路时的类型,没有隐式转换;
除非十分明确,否则不要依赖隐式转换,写代码时,为了程序的健壮,请显式的转换;
例,弱类型,都转为字符串,再相加:
console.log(a = 3 + 'magedu', typeof(a));
console.log(a = null + 'magedu', typeof(a));
console.log(a = undefined + 'magedu', typeof(a));
console.log(a = true + 'magedu', typeof(a));
输出:
3magedu string
nullmagedu string
undefinedmagedu string
truemagedu string
例,数字:
console.log(a = null + 8, typeof(a)); //null-->0
console.log(a = undefined + 8, typeof(a)); //undefined没法转换成一个对应的数字
console.log(a = true + 8, typeof(a)); //true-->1
console.log(a = false + 8, typeof(a)); //false-->0
输出:
8 'number'
NaN 'number'
9 'number'
8 'number'
例,bollean:
console.log(a = null + true, typeof(a)); //0+1
console.log(a = null + false, typeof(a)); //0+0
console.log(a = undefined + true, typeof(a)); //undefined没法转换成一个对应的数字
console.log(a = undefined + false, typeof(a));
console.log(a = null & true, typeof(a)); //0&1,与即按位乘
console.log(a = undefined & false, typeof(a)); //NaN&0,结果0
输出:
1 'number'
0 'number'
NaN 'number'
NaN 'number'
0 'number'
0 'number'
例,短路:
console.log(a = null && true, typeof(a)); //null
console.log(a = false && null, typeof(a)); //false
console.log(a = false && 'magedu', typeof(a)); //false
console.log(a = true && 'magedu', typeof(a)); //magedu
console.log(a = true && '', typeof(a)); //
输出:
null 'object'
false 'boolean'
false 'boolean'
magedu string
string
例,null:
console.log(a = null + undefined, typeof(a)); //NaN
输出:
NaN 'number'
转义字符:
\0,null字节;
\b,退格符;
\f,换页符;
\n,换行符;
\r,回车符;
\t,tab制表符;
\v,垂直制表符;
\',单引号;
\",双引号;
\,反斜杠字符;
\XXX,由从0-377最多三位八进制数XXX表示的Latin-1字符,如\251是版权符号的八进制序列;
\xXX,由从00-FF的两位十六进制数字XX表示的Latin-1字符,如\xA9是版权符号的十六进制序列;
\uXXXX,由四位十六进制数字XXXX表示的unicode字符,如\u00A9是版权符号的unicode序列,见unicode escape sequences(unicode转义字符);
\U{XXXX},unicode代码点code point转义字符,如\u{2F804}相当于unicode转义字符\uD87E\uDC04的简写;
将一个值使用单引号或双引号引用起来就是字符串;
ES6提供了反引号定义一个字符串,可支持多行和插值;
注:字符串插值,py3.6支持;
例:
let name = 'tom';
let age = 18;
let c = `line1
line2
Myname is ${name}. I am ${age}`;
console.log(c)
输出:
line1
line2
Myname is tom. I am 18
字符串操作方法:
和py类似;
''. #查看方法
例:
let school = 'magedu';
console.log(school.charAt(2)); //提供索引号返回对应的元素
console.log(school[2]); //同school.charAt(2)
console.log(school.toUpperCase()); //转大写
console.log(school.concat('.com')); //连接
console.log(school.slice(3)); //切片
console.log(school.slice(3, 5)); //前包后不包
console.log(school.slice(-5, -1)); //支持负索引
输出:
g
g
MAGEDU
magedu.com
edu
ed
aged
例:
let url = 'www.magedu.com';
console.log(url.split('.'));
console.log(url.substr(7, 2)); //返回子串,从何处开始,取多长
console.log(url.substring(7, 10)); //返回子串,从何处开始,到什么为止,前包后不包
console.log(url.substring(7, 9));
输出:
[ 'www', 'magedu', 'com' ]
ed
edu
ed
例:
let s = 'magedu.edu';
console.log(s.indexOf('ed')); //返回索引号
console.log(s.indexOf('ed', 6)); //指定位置开始找
console.log(s.replace('.edu', '.com')); //替换
输出:
3
7
magedu.com
例:
let s = ' \tmag edu \r\n';
console.log(s.trim()); //去除两端的空白字符,trimLeft、trimRight是非标函数,不要用
输出:
mag edu
js中,数据均为双精度浮点型,范围只能在-(2^53-1)到2^53-1之间,整型也不例外;
数字类型还有三种符号值:
+Infinity,正无穷;
-Infinity,负无穷;
NaN,not a number,非数字;
二进制,0b0010、0B110;
八进制,0755,注意,0855被认作是十进制,因为8不在二进制中,ES6中最好使用0o前缀表示八进制;
十六进制,0xAA、0xff;
指数,1E3即1000,2e-2即0.02;
常量属性:
var biggestNum = Number.MAX_VALUE;
var smallestNum = Number.MIN_VALUE;
var infiniteNum = Number.POSITIVE_INFINITY;
var negInfiniteNum = Number.NEGATIVE_INFINITY;
var notANum = Number.NaN;
数字的方法:
Number.parseFloat(),常用,把字符串参数解析成浮点数,和全局方法parseFloat()作用一致;转换失败为NaN;
Number.parseInt(),常用,把字符串解析成特定基数对应的整型数字,和全局方法parseInt()作用一致;转换失败为NaN;
Number.isFinite(),判断传递的值是否为有限数字;
Number.isInteger(),判断传递的值是否为整数;
Number.isNan(),判断传递的值是否为NaN;
Math,内置数学对象Math,提供了绝对值、对数指数运算、三角函数运算、最大值、最小值、随机数、开方等运算函数,提供PI值;
例:
console.log(parseInt('1100'));
console.log(Number.parseInt('1100'));
onsole.log(Number.parseInt('abc')); //X,NaN
输出:
1100
1100
NaN
算术运算符:+-*/%
单目运算符:
++,自增;
--,自减;
i++,先用i,用完之后i再自增加1;
++i,i先自增,再使用i;
i++和i+=1是两码事:
i++是plusplus(i)直接加未进栈;
i+=1,i=i+1,plus(i+1),此函数与栈有关;
注:
java中的i++和i+=1是一回事,因此最终转的字节码是i++;
比较运算符:
<,>,>=,<=,
!=,==,宽松相等,进行类型转换;
!==,===,严格相等,不进行类型转换,内容和类型都关注时用严格相等;
逻辑运算符:
&&,与;
||,或;
!,非;
位运算:
&,|,^,~,<<,>>
位与,位或,异或,取反,左移,右移;
三元运算符:
条件表达式?真值:假值 //等价于if...else结构
if (条件表达式) {
真值
} else {
假值
}
console.log('3' > 30 ? 'true' : 'false');
输出:
false
注:
py中无三目运算符,类三目运算符为:
真值 if 条件 else 假值 #如果语句简单不超过3行,可用此处的类三目运算符
逗号操作符:
js允许多个表达式写在一起;
let a=4+5,b=true,c='a' > 2 ? 't' : 'f';
console.log(a,b,c)
输出:
9 true 'f'
其它:
instanceof,判断是否属性指定类型,要求必须使用new关键字声明创建的,明确使用类型定义变量,可用于继承关系的判断;instanceof用得少,typeof用的多;
typeof,返回对象的类型字符串;
delete,操作符,删除一个对象(an object)或一个对象的属性(an object's property),或一个数组中某一个键值(数组元素,an element at a specified index in an array);隐式类型的声明都可删除,如x = 42,myobj = new Number();隐式声明定义的变量可用delete删掉,var、let预定义的变量不能用delete删;
in,如果指定的属性在对象内,则返回true,如数组Array对象中的索引号和length都是其属性,console.log(0 in trees);console.log('length' in trees),元素(即值)不能用in;
运算符优先级:
.,[]
(),new
!,~,-,+,++,--,typeof,void,delete
*,/,%
+,-
<<,>>,>>>
<,>,<=,>=,in,instanceof
==,!=,===,!==
&
^
|
&&
||
?:
=,+=,-=,*=,/=,%=,<<=,>>=,>>>=,&=,^=,|=
例:
console.log(1/2);
console.log(1/0); //无异常,返回无穷
console.log(5%3);
输出:
0.5
Infinity
2
例:
let i = 0;
let a = i++; //let a=i;i++
console.log(a, i);
console.log(a, i++);
a = ++i;
console.log(a, i);
输出:
0 1
0 1
3 3
例,C、C++、java面试题:
i = 0;
let a = ++i+i+++i+++i; //单目运算符(++)优先级高于双目运算符(+),(++i)+i+(++i)+(++i)
console.log(a);
输出:
7
例:
console.log(100 > '200');
console.log(300 > '200');
console.log(300 > '2000');
console.log(300 > '2a');
console.log(300 == '300');
console.log('200' == '200');
console.log(300 === '300');
console.log(200 === 200);
输出:
false
true
false
false
true
true
false
true
例:
console.log('abc' instanceof String); //false
a = new String('abc');
console.log(a instanceof String); //true
console.log(typeof(a));
console.log(typeof('abc'));
console.log(typeof(1));
console.log(typeof('abc') == 'string');
输出:
false
true
object
string
number
true
例:
x = 42; //隐式声明,严格模式下会报错
var y = 43; //ES6之前用var声明变量,ES6开始不推荐使用
let z = 44; //ES6推荐用let
myobj = new Number(); //隐式声明,创建实例
myobj.h = 45; //创建属性h
console.log(delete x); //true,can delete if declared implicitly
console.log(delete y); //false,cannot delete if declared with var
console.log(delete z); //false,cannot delete if declared with let
console.log(delete Math.PI); //false,cannot delete predefined properties
console.log(delete myobj.h); //true,can delete user-defined properties
console.log(delete myobj); //true,can delete if declared implicitly
输出:
true
false
false
false
true
true
例:
var trees = new Array(1,2,3,4,5);
for (var i=0;i<trees.length;i++)
console.log(trees[i]);
delete trees[3]; //仅清除元素,位置仍留着(删后为undefined),整个数组中元素位置未移动
for (var i=0;i<trees.length;i++)
console.log(trees[i]);
输出:
1
2
3
4
5
1
2
3
undefined
5
例:
let trees = new Array('a','b','c','d','e','f');
console.log(0 in trees); //true,0在数组对象的index中,注意此处0是索引而不是值
console.log(3 in trees); //true
console.log(6 in trees); //false
console.log('c' in trees); //'c'不是属性而是值,
console.log('length' in trees); //true,length是对象的属性
delete trees[3];
console.log(3 in trees); //false
for (var i=0;i<trees.length;i++)
console.log(trees[i]);
输出:
true
true
false
false
true
false
a
b
c
undefined
e
f
例:
let mycar = {
make: 'Honda',
model: 'Acord',
year: 2018
}
console.log('make' in mycar);
console.log('model' in mycar);
输出:
true
true
基本表达式,和py差不多;
解析式和py相似,但在ES6中非标准不推荐;
生成器推荐使用生成器函数,ES6开始支持;
function表示普通函数,function*表示生成器函数;
每次调用next()返回一个对象,该对象包含2个属性,value和done,value表示本次yield表达式的返回值,done为boolean类型(false表示后续还有yield语句执行,如果执行完或return后done为true);
function inc() { //java风格
}
function inc() //C++风格
{
}
死循环:
方式一,while (true) {}:
while (1) {
}
或
while (-1) {
}
方式二:
for (;;) {
}
例,解构:
使用...解构;
js的解构很灵活;
var parts = ['shoulder','kness'];
var lyrics = ['head',...parts,'toes'];
console.log(lyrics);
function f(x,y,z) { //参数解构
console.log(x+y+z);
}
var args = [2,3,4];
f(...args); //函数调用
输出:
[ 'head', 'shoulder', 'kness', 'toes' ]
9
例,生成器函数:
function* inc() { //function表示普通函数,function*表示生成器函数
let i = 0;
while (1) {
yield (++i);
}
}
let g = inc();
console.log(g.next()); //
console.log(g.next());
输出:
{ value: 1, done: false }
{ value: 2, done: false }
例:
function* inc() {
let i = 0;
let j = 7;
while (true) {
yield i++;
if (!j--) return 100;
}
}
let g = inc();
for (let i=0;i<10;i++)
// console.log(g.next().value)
console.log(g.next());
输出:
{ value: 0, done: false }
{ value: 1, done: false }
{ value: 2, done: false }
{ value: 3, done: false }
{ value: 4, done: false }
{ value: 5, done: false }
{ value: 6, done: false }
{ value: 7, done: false }
{ value: 100, done: true }
{ value: undefined, done: true }
免责声明:本站发布的内容(图片、视频和文字)以原创、转载和分享为主,文章观点不代表本网站立场,如果涉及侵权请联系站长邮箱:is@yisu.com进行举报,并提供相关证据,一经查实,将立刻删除涉嫌侵权内容。