JS学习笔记整理一 基础中的基础

学习资源来自于js高程,有一部分参考犀牛。基本上是按照js高程的目录来学的。笔记记了些重点和引伸。还有一些参考网站。javascript

JavaScript简介

Javascript是ecma-262的一种实现。它由三部分组成:ecmascript、bom、dom。ecmascript自己是ecma-262定义的标准,不依赖于具体环境,也不包含输入输出定义。宿主环境提供ecmascript的具体实现和交互的扩展。好比浏览器、node、flash等。html

你们能够百度一下ecma发展的时间线vue

es4夭折是由于部份内容太过激进等于从新定义一门语言,缺少实践检验,微软和雅虎反对方话语权很大。不过当年如日中天的adobe仍是本身用as3.0实现了es4。es4的部份内容将在es6中体现。从es3到es6至关于15年的沉淀。html5

es5实际就是es3.1版本。是一个温和过分版本。java

js引擎

能解析并能运行js代码的解释器node

浏览器一般会有js引擎,js刚出来时就是运行在浏览器中,做为客户端语言使用。常见的js引擎有:es6

  • chrome v8
  • firefox spiderMonkey
  • edge chakra
  • node基于v8,只保留es核心,没有dom和bom。增长了事件驱动非阻塞I/O模型,更加轻量和高效。

DOM

dom0不算标准chrome

Dom1

1998年成为W3C的推荐标准。同ecma262相似,dom并不止针对js。包含dom core、dom html两个模块编程

Dom2

2000年底发布,包含dom views、dom events、dom style、dom traversal and rangejson

Dom3

2004年发布包含dom load and save、dom validation、dom style核心扩展

Dom级别本质上说是版本。

BOM

浏览器对象模型bom。由于做为javascript实现的一部分,没有相关标准。原来比较看宿主环境。可是html5致力于把不少bom功能写入标准,有望能改变这种现象。

在HTML中使用JavaScript

<script>标签,属性src, async,defer,这三个属性都只针对外部文档,延迟或异步执行。其余的属性基本没什么用。

在<script>嵌入的代码中,使用</script>会报错。须要用转义字符<\/script>

引用外部js尽可能用标签对,别用省略写法。

当浏览器遇到<script>时,便会解释运行js内容,当其中内容都解释运行完毕,才会继续呈现html中的其余内容。所以<script>的位置很重要。若是把<script>放入,有时候加载外部文件,好比被墙的google会阻塞页面的呈现。若是把<script>放入页面最末尾,当页面其余内容渲染完毕,再执行js也未必OK,由于有可能js当中也有渲染页面的代码,这样会形成闪烁。 <script>内容放置的位置要看具体状况。

须要注意的defer延迟运行,对嵌入的脚步无效。同时,多个延迟脚本不必定能按顺序执行。建议这类脚本仍是放在文档的最末尾比较保险。

defer和async都是针对外部脚本。 使用defer延迟运行,多个延迟脚本不必定能按顺序执行。设置为async异步脚本,不会阻塞页面内容。要保证与其余脚本没有依赖关系,由于他们不保证执行顺序。建议异步脚本不要在加载期间修改dom。

提到<script>就须要说明一下跨域问题。<script>和均可以跨域。能够加载其余域的图片资源。<script>则能够调用外部的js。同时能够经过get方式传递参数。远程代码能够返回任意内容。

转载:跨域问题实际测过的方法:jsonp,iframe+document.domain,cors跨域资源共享。

基本概念

js区分大小写。首字符必须为字母、下划线、$。非首字符可用数字。

标识符驼峰写法,或者$开头,或者下划线分隔写法。

"use strict"
可写在函数体内。
复制代码

关键字和保留字

关键字是控制语句的开始和结束,用来执行特定操做。关键字不能用做标识符。都是如今语句里用的。

break do while this function var newcontinue typeof instanceof return void

if else case switch with try catch finallythrow for delete debugger default

保留字是一些保留下来不能做为标识符的,未来有可能做为关键字。

好比class interface longchar public private……

第5版对于以上有些变化。但尽可能编程时避免雷区。

变量

Js的变量是松散类型的。Js声明变量时,分配给标识符 存储区域,并将标识符和做用域进行绑定。

数据类型

Ecmascript有五种简单数据类型:

  • Null
  • Boolean
  • String
  • Number
  • Undefined

一种复杂数据类型:

  • Object

只声明未初始化和未声明过的变量都会显示undefined.

学过as和js,有时候会把变量声明的方式搞混。actionscript里有一种写法。A:array=new Array();在js里不适用。js就是弱类型。不必用冒号加类型。若是这么写会报错。

var a;
// var b; 未声明b
console.log(a);//undefined
console.log(b);//报错
复制代码

可是使用typeof

var a;
// var b; 未声明b
console.log(typeof a);  //undefined
console.log(typeof b);  //undefined 不会报错
复制代码

所以,对于没有声明的变量,typeof是惟一可执行的操做。在写程序的时候,咱们应该显式初始化变量,这样咱们再使用typeof时,看到undefined时,就知道这个变量是未声明的。

var c=null;
console.log(c);//null
console.log(typeof c);//object
复制代码

null值表示一个空对象指针。

若是定义的变量未来要保存对象,那么能够先给其null值。所以,看到null,咱们就应该知道它是干吗的。

另外:

console.log(null==undefined);//true
var car=null;
if(car!=null){
//执行某些操做
}//这样是能够的。
复制代码

这里就存在一个问题。如何判断变量是null呢?

if(car==null){}//这样是不许确的,由于undefined也能够==null。
复制代码

利用typeof也不行,由于会返回object。

if(car===null){}//这样写比较简单。
复制代码
Number类型

不要测试某个特定的浮点数值,好比,0.1+0.2结果不是0.3。这是基于IEEE754数值浮点计算的通病。解决这个问题,一般是把浮点数转换成整数再计算。Es6中出现了一个新的常数,Number.EPSILON,而这个值等于2^-52。相似于取极限,(0.1+0.2)-0.3小于Number.EPSILON就能够认为0.1+0.2等于0.3。 关于Number()和parseInt()的区别。

var a="22asdfs";
console.log(parseInt(a));//22
console.log(Number(a));//NaN
var a="22.5";
console.log(parseInt(a));//22 int就是整形的意思,因此会忽略小数点。
console.log(Number(a));//22.5
var a="";//空字符,加空格也如此
console.log(parseInt(a));//NaN
console.log(Number(a));//0
var a="22e-6";
console.log(parseInt(a));//22
console.log(Number(a));//0.000022
var a="0x111";
console.log(parseInt(a));//273
console.log(Number(a));// 273
var a="AF";
console.log(parseInt(a,16));//175
console.log(Number(a));//NaN 
复制代码

Number()能够对任意类型作转换,而parseInt()则只能对字符串作转换。parseInt有第二个参数,作基数。Number()对boolean的false转为0,true转为1。Null转换为0,undefined转换为NaN。

parseFloat只识别十进制数,忽略前导0,十六进制数0x开头,只能识别为0。第二个小数点无效。无第二个参数。

String类型
  1. 字符字面量 记住一些常见的转义字符,使用反斜\开头。\n,\t,\r,\b等。使用双字节字符length可能不会返回准确字符数目。

  2. 字符串特色 字符串一旦建立值就不能改变!一旦想改变某变量保存的字符串,须要先销毁原来的字符串,再使用另外一个包含新值的字符串填充变量。也是由于这个特色,一些旧版浏览器拼接字符串效率低。

  3. 转换为字符串 把一个值转换为字符串有两种方法,一种使用toString()方法,另外一种使用类型转换String()函数。 null和undefined没有toString属性。因此

    var chr=null
    chr.toString()//报错
    复制代码

    可是,使用String()转型能够。其首先查看是否有toString()方法,有则调用。若是值是null则返回” null”,是undefined则返回”undefined”。

Object类型

每一个Object对象都有如下属性和方法:

constructor,hasOwnProperty,toString,valueOf,isPrototypeOf,propertyIsEnumerable,toLocalString。 能够经过下面方法看到,全部对象都继承自Object的原型对象。

console.log(Object.getOwnPropertyNames(Object.prototype))
复制代码

Objecet.keys和Object.getOwnPropertyName的区别:Object.keys列举对象自有可枚举属性。 Object.getOwnPropertyName列举对象的自有属性。

能够经过propertyIsEnumerable来检查属性是否可枚举

console.log(Object.prototype.propertyIsEnumerable("toString"));
//false
复制代码

另外for in能够列举对象的全部可枚举属性。包括继承和非继承的属性。

操做符

一元操做符

一元加减运算符。非数字应用一元加减运算符,能够类型转换。

var chr="10";
console.log(+chr+2);//12
console.log(chr+2);//102
复制代码
位操做符

有符号整数,正负转换一概反码加一。 好比用四位表示二进制有符号整数。

0000 表示0
0001表示1 1111表示-1 0010表示2 1110表示-2 0011表示3 1101表示-3 0100表示4 1100表示-4 0101表示5 1011表示-5 0110表示6 1010表示-6 0111表示7 1001表示-7

负值=取反(正值)+1 这个方法通常用做负数求补。利用按位非的特色。~~两个按位非能够对数字下取整。能够想象,这比Math.floor效率快。

计算机中的符号数有三种表示方法,即原码(转载)反码(转载)补码(转载)。数值一概用补码来表示和存储。缘由在于,使用补码,能够将符号位和数值域统一处理。

  1. 按位非 就是按位取反。 符号~ 用上面的例子来说就是负值减一 取反(正值)=负值-1

  2. 按位与 很方便的判断奇偶,奇数&1=1,偶数&0=0。

    If(数字&1){
    //奇数
    }else{
    //偶数
    }
    复制代码
  3. 按位或

也能够用来取整,数字|0 ,包括不过~~感受看起来更舒服。

关于位操做,能够结合计算机组成原理第二章运算方法和运算器来看。

  1. 按位异或能够用来判断乘法符号位。相同状况0,不一样为1。符号求补阵列加法器。

按位异或还能够作数值交换。这种状况不多见,能够不用额外声明变量。

a^=b;
b^=a;
a^=b;
复制代码

对2求补可用按位扫描技术来执行所需求补操做。从右向左找到第一个“1”,从这位到右保持不变,这位左侧的数字所有求反就OK。

直接补码阵列乘法器,符号位参与运算,因此省去对2求补和补位运算,提升效率。了解便可。

对于位操做符有更深入直观的认识。一些运算(例如取整)使用位操做符能大大提升效率。

位运算符的妙用:转载:https://www.cnblogs.com/happy1992/p/7064114.html

布尔操做符

逻辑非,!!两次至关于类型转换Boolean(),返回所求内容对应的布尔值。

逻辑与 && 短路操做符。若是左侧可以决定结果,则不会继续对右侧求值。 基于这种原理,每每在使用上来作递进的判断。好比先判断是否有对象Car,若是有,判断这个对象下面是否有属性a,若是有,对属性a赋值。肯定具有某一条件(左侧),则返回(右侧)

var me=null;
//程序某一处me={high:185,skin:"black"};
var b=me&&me.high;
console.log(b);
复制代码

逻辑或 || 也是操做符。当左侧为true,返回左侧,不对右侧求值。当左侧为false则返回右侧值。常常用在给变量赋值的状况,若是没有初始化的值则返回右侧的默认值。(左侧)不符合条件,则返回(右侧)。

var me={skin:"black"};
//程序某一处me.high=180;
var b=me.high||185;
console.log(b);
复制代码
乘性操做符

乘法中操做符几个特殊的结果:

Infinity*0为NaN。 //别忘了NaN!=NaN NaN与任何数都为NaN, Infinity与非0数仍是(+-)Infinity。

除法中几个特殊结果:

NaN与任何数都为NaN Infinity除Infinity和0除0都为 NaN

求模中几个特殊结果:

被除数是0结果为0 被除数是有限数,除数是无限大,结果是被除数 其余凡是你认为没结果的都是NaN

加性操做符

加法当有字符串为操做数时,对于其余数据类型用toString()方法,null和undefined这两种使用String();

可用()来影响操做顺序和转换类型。

减法规则:存在除number之外简单数据类型时,先调用Number()。若是存在Object类型,先经过valueOf()转换。若是不存在则先toString()再Number()转为数字。Null直接用Number()转为0,undefined为NaN。

总结为在操做数分别为字符串和数字时,加法当字符串拼接,减法当数字相减。

关系操做符

对于null和undefined的存在,书上没有具体阐述。可是,关系操做符比较偏心转数字,加号操做符偏心转字符串。针对和数字的比较有:

var a=undefined;
console.log(a<1);//false ,若是转换了类型,则按照规则,undefined转为数字NaN
console.log(a>1);//false
var a=null;
console.log(a<1);//true根据规则null转成0.
console.log(a>1);//false

console.log(a<"a");//false 即使有字符串,也是转数字的,
//a变成NaN,所以始终是false
console.log(a>"a");//false
复制代码
相等操做符

==操做符可能须要类型转换,null和undefined则不转换。 ===不进行转换即相等才返回true。

条件操做符

也叫三目(元)运算符。在ecmascript中最灵活的一种,大神的代码中特别常见。特别相似于if…else…

条件?表达式1 :表达式2
复制代码

三目运算符是能够嵌套使用的。好比:

条件1?表达式1:条件2?表达式2:条件3?表达式3:表达式4

能够将当即执行函数表达式放入三目运算符。由于这样能够封闭做用域,传参,返回值。结合赋值语句使用很强大。

在vue里颇有用。

不过在后面研究label和break的时候,发现三目运算符不能带break和continue一块儿用,会报错。

语句

with语句

将代码的做用与设置到一个特定的对象中。在with代码块内部,每一个变量首先被认为是局部变量,若是局部环境找不到变量的定义,就会查找特定对象做用域是否有同名属性。若是有,则以特定对象中属性值做为变量的值。 with严格模式会报错

函数

关于函数表达式,函数声明,匿名函数的分析,(function(){})();

何为当即执行函数Immediately-InvokedFunction Expression (IIFE)

转载:https://www.cnblogs.com/zichi/p/4401755.html

转载:https://blog.csdn.net/linshichen/article/details/78328125

这部分能够结合红皮书第四章变量、做用域和内存问题理解

Js堆栈、浅拷贝、深拷贝、基本类型、引用类型:

转载:https://www.cnblogs.com/chengguanhui/p/4737413.html

相关文章
相关标签/搜索