JavaScript - week4

112 阅读10分钟

ES5

保护对象

四大特性

Object.defineProperties(obj,{
    "属性名":{
            value:实际保存值
            writable:true/false//开关:控制着这个属性名是否可以被修改
            enumerable:true/false//开关:控制着这个属性名是否可以被for in 循环遍历到
            configurable:true/false//开关:控制着这个属性名是否可以被删除-这一句是总开关,一旦设置为false,其他特性不允许再修改
    }
})

三个级别

1、防拓展:禁止给对象添加新属性
    Object.preventExtensions(obj);

2、密封:禁止给对象添加新属性和删除属性
    Object.seal(obj);
    
3、冻结:禁止给对象添加和删除和修改
    Object.freeze(obj);

数组的新API

判断

every

判断的结果一定是一个布尔值
every:每一个-要求每一个元素都要满足,结果才为true,只要有一个不满足就为false
语法:var bool = arr.every(function(val,i,arr){
        return 判断条件
})
//val -当前值
//i - 当前下标
//arr -数组本身

some

要求元素都不满足才为false,只要有一个满足就为true
语法:var bool = arr.some(function(val,i,arr){
        return 判断条件;
})

遍历

forEach

遍历数组,直接修改原数组
语法:arr.forEach(function(val,i,arr){
        直接做操作
})

map

遍历数组:不修改原数组返回一个新数组
语法:var newArr = arr.map(function(val,i,arr){
        return 操作的结果 
})

过滤和汇总

过滤

过滤:筛选出自己想要的,但是不会修改原数组
语法:var subArr = arr.filter(function(val,i,arr){
        return 判断条件;
})

汇总

将数组中的每个元素汇总到一起
语法:var sum = arr.reduce(function(prev,val,i,arr){
            rerurn prev+val;
},基础值);//基础值会和最后的结果加在一起

Object.create();

根据父对象创建子对象,继承已经设置好了
语法:var 子对象 = Object.creat(父对象,{
        "自有属性名":{四大特性},
        ....
});

严格模式

开启:在你的任何作用域的顶部加上一句话:"user strict";
功能:1、禁止给未声明的变量赋值-解决全局污染
     2、静默失败升级为报错

call/apply/bind.

call/apply

临时替换了函数中的this-借用
语法:函数名.call(借用的对象,实参,...);-单独传入每一个实参
     函数名.apply(借用的对象,arr);-只能传入一个实参是一个数组,apply其实会悄悄的将数组打散
强调:call/apply,相当于立刻调用函数,立即执行

bind

永久替换了函数中的this - 买
3件事:
 1、创建了一个和原函数完全相同功能的新函数
 2、将新函数中的this永久绑定为了指定对象,别人都借不走了
 3、将新函数中的部分参数永久固定
 用法:var 新函数=原函数.bind(指定对象,永久实参,...) - 不是立刻执行的,需要自己调用
 强调:bind绑定的新函数没有办法被call/apply借走

固定套路

1Math.max/min.apply(Math,arr);
2Object.prototype.toString.call/apply(arr);
3、***类数组转为普通数组:类数组名称=Array.prototype.slice.call/apply(类数组);

ES6

模板字符串

可以在字符串中放入变量-不需要再做字符串拼接,再字符串中实现了一个简单的js的环境
语法:'我的名字叫${name}'

块级作用域

let 变量名 = 值;
作用:1、禁止声明提前
     2、添加了块级作用域
     3、记录着当前触发事件的元素的下标

箭头函数

作用:简化回调函数
公式:去掉function,()和{}之间添加=>,形参只有一个,则省略(),函数体如果只有一句话,省略{},函数体只有一句话并且是returnreturn和{}都省略

DOM

什么是DOMDocument Object Model(文档对象模型)
将每一个标签/元素/属性/文本/注释,看做了一个DOM节点/元素/对象(提供了一些操作元素的属性和方法)

面试题

HTML/XHTML/DHTML/XML分别是什么?
1HTML - 网页
2XHTML - 更严格的网页
3DHTML - 动态的网页:D:Dynamic:其实并不是新技术、新概念,是将现有技术的整合的统称,使我们的网页在离线状态依然具有动态效果
		DHTMLHTML+CSS+JS(dom);
4XML - 数据格式

DOM

原本是可以操作一切结构化文档的HTMLXML,后来为了方便各类开发者分为三部分
1、核心DOM:既可以操作HTMLXML又可以操作XML
2HTML DOM:只能操作HTMLAPI简单
3XML DOM :只能操作XMLXML基本已经淘汰了-现在最流行的数据格式JSON

开发建议:优先使用HTML DOMHTML DOM 满足不了的再用核心DOM补充

DOM 树

树根:document-不需要创建,一个页面只有一个document对象,由浏览器的JS解释器自动生成
可以通过树根找到每一个DOM元素/节点/对象,提供了很多很多的API

DOM三大属性

1XX.nodeType:描述节点的类型
    document节点:9
    element节点:1
    attribute节点:2
    text节点:3
    
2、xx.nodeValue:属性节点的值,说白了获取属性值

3、xx.nodeName:节点的名称-判断xx是什么属性
    注意:返回的是一个全大写的标签名

通过关系获取元素

父:xx.parentNode
子:xx.children - 集合,只能找到子级儿子,不能找后代
第一个儿子:xx.firstElementChild
最后一个儿子:xx.lastElementChild
前一个兄弟:xx.previousElementSibling
后一个兄弟:xx.nextElementSibling

递归

简单来说就是函数中,又一次调用了函数自己,迟早有一天会停下来
何时使用:遍历DOM树,专门用于遍历层级不明确的情况,既可以遍历层级不明确的DOM,也可以遍历层级不明确的数据

如何递归:2function 函数名(root){
        1、第一层你要做什么操作
        
        2、判断他有没有下一级,如果有下一级再次调用此函数,只不过传入的实参是他的下一次
    }

算法:深度优先!优先遍历当前节点的子节点,子节点遍历完毕才会跳到兄弟节点
缺点:同时开启大量的函数调用,浪费内存,只有一个情况采用:遍历层级不明确

TreeWalker

遍历层级不明确的API,专门为遍历层级不明确的DOM准备
如何:
    固定公式
    1、创建tw:
        var tw = document.creatTreeWalker(根元素,NodeFilter.SHOW_ELEMENT);
    2、反复调用nextNode方法找到每一个元素
        while((node=tw.nextNode())!=null){
            node要做什么操作;
        }

API直接查找元素

1、通过HTML的一些特点去找元素
    1、id:var elem = document.getElementById("id") - 找到了是单个元素,没找到null
    2、tagname/class/name:var elems = document.getElementsByTagName/ClassName/Name("标签名/class名") - 找到了是个集合,没找到是个空集合

2、通过css选择器去获取元素:
    1、单个元素:var elem = document.querySelector("任意css选择器");
        强调:万一选择器匹配到多个,只会返回第一个,没找到则为null
    2、多个元素:var elem = document.querySelectorAll("任意css选择器");
        强调:找到了返回集合,没找到返回空集合

面试题

getXXX和querySeletorXXX 有什么区别
 1、返回结果不同
         1、getXXX,获取到返回的十一个动态集合HTMLCollection
         2、quertSeletorXXX,获取到返回的是一个静态集合NodeList
  动态集合:根据DOM树的改变,是动态集合也一起改变,每一次修改DOM树,都会悄悄的再次查找DOM
      缺点:每次都会悄悄重新查找,效率低,不能使用forEach
  静态集合:每一次修改DOM树,静态集合不会发生变化,只会认准你找的时候的第一次找到的结果
      优点:每次不会悄悄重新查找,效率高,可以使用forEach

操作元素

元素的内容

1、elem.innerHTML:获取或设置开始标签到结束标签之间的HTML代码,没有兼容性问题,可以识别标签
    获取:elem.innerHTML
    设置:elem..innerHTML = "新内容"
2、elem.textContent:获取或设置开始标签到结束标签之间的纯文本,具有兼容性问题,不能识别标签
    获取:elem.textContent
    设置:elem.textContent = "新内容"IE:elem.innerText;//原本只有老IE可以使用,但是随着各个浏览器的发展,主流浏览器也开始使用
3、input.value:获取或设置单标签(能写内容的单标签)的内容
    获取:input.value
    设置:input.value = "新内容"

元素的属性

获取属性值

核心DOM:elem.getAttribute("属性名");
HTML DOM:elem.属性名;

设置属性值

核心DOM:elem.setAttribute("属性名","属性值");
HTML DOM:elem.属性名 = "属性值"

删除属性

核心DOM:elem.removeAttribute("属性名")
HTML DOM:elem.属性名="";

判断属性

只能判断有没有,不能判断具体是什么
核心DOM:elem.hasAttribute("属性名");
真的想要判断,更推荐:
			if(elem.getAttribute("class")=="d1"){
				使用获取的方式能判断出具体是什么class
			}

强调

1class写为className
2、只能操作标准属性,不能操作自定义属性
3、删除的时候,删不干净,有的属性删不干净依然具有功能,比如href没有属性值默认为属性、disabled就算没有属性值依然是禁用操作

元素的样式

内联样式

优先级最高,一定会覆盖其他的样式
仅仅当前元素可用,不会牵一发动全身
获取样式:elem.style.css属性名
设置样式:elem.style.css属性名 = "css属性值"

唯一的缺点:获取样式时,只能获取内联样式

样式表

//1、获取你想要操作的样式表
        var sheet=document.styleSheets[1];
//2、获取这个样式表中所有的样式规则
	var rules=sheet.cssRules;
//3、数出你想要操作的那个样式规则
	var rule=rules[30];
//4、操作:获取和设置
	console.log(rule.style.background);
	rule.style.background="purple"

创建元素和渲染DOM数据

1、创建空标签:
    var elem = document.creatElement("标签名");
2、为这个空标签添加必要的东西(属性或事件)
    elem.属性名 = "属性值";
    elem.on事件名 = function(){}
3、将在内存中创建的元素渲染到DOM树上
    父元素.appendChild(elem);//将elem追加到父元素里面当了最后一个儿子
    父元素.insertBefore(elem,已有子元素);//将elem追加到父元素里面当了儿子,会插在已有子元素的前面 - 导致所有元素的下标都会改变
    父元素.replaceChild(elem,已有子元素);//将elem追加到父元素里面当了儿子,会替换掉已有子元素

删除元素

elem.remove();

--核心DOM全部完毕了,总结DOM到底干了什么事?
增、删、改、查(DOM结构:元素、文本、属性、样式)

HTML DOM常用对象

image对象

仅仅简化了创建语句
创建: var img = new Image();//完全等效于var img = document.createElement("img");

form对象

简化了查找元素
查找form元素:var form = document.forms
查找form元素中的表单控件:var input = form.elements
专属事件:f








































orm.onsubmit = function(){
    //提交事件,只会在提交的一瞬间触发:防止用户输入错误也能提交
    return false;//阻止条件
}

select对象

属性:1、select.options;//得到select下面所有的option,完全等效于xx.children
      2、select.selectedIndex;//获取当前选中项的下标-只要是做联动就必然会用到
方法:1、select.add(option);//完全等效于appenChild
      2、select,remove(i);//删除掉下标i的option
专属事件:select.onchange = function(){//只有选中项发生变化的时候才会触发}

option对象

创建:var opt = new Option("innerHTML","value");
如果想要一句话将option创建出来放入select中:
    select.add(new Option("内容","值"))

浏览器提供了3个弹出框

   1、用户输入框:var user=prompt("提示文字","默认值");

   2、警告框:alert("警告文字");

   3、用户确认框:var bool=confirm("提示文字");

BOM

Browser Object Model :浏览器对象模型:专门用于操作浏览器的API
重点:定时器、事件对象even t