1 数组中的循环
1.for
2.for(const value of array)
3.for(const key in array)
4.lis.forEach(function (item)
通过4来实现点击变灰
let lis = document.querySelectorAll("ul li");
lis.forEach(function (item) {
console.log(item);
//item.innerHTML="lxj live";
item.addEventListener('click',function () {
this.classList.toggle('disable');
item.innerHTML="changed";
});
});
2js中的数据类型Symbol
1.它是一个数据类型,具有唯一性。它的描述可以用description查看
2.它在类中石私有类型,用普通方式(for in,for of)遍历类中的key,如果key是Symbol类型,则不会被打印出来。用特殊方式可以查看。如
const key of Object.getOwnPropertySymbols(hd)
只能遍历到Symbol类型,不遍历所有key
const key of Reflect.ownKeys(hd)
则可以遍历类中所有的key
3.总结:对象中想要隐私的属性用Symbol。
3 set
1.特点:元素不能重复,会唯一存在。
2.has(),size,delete(x),clear(),values()或keys()或entries()
是否存在某元素,set的元素数量,删除x元素,清空set,查看元素。
3.类型转换:
1.Array.from(set1),将set转换为数组
第二种方法:[…set]
2.数组转set
arr2 = new Set(arr1)
<script>
let xj = new Set("123456789");
xj = new Set( [...xj].filter(item => item <5));
//xj = new Set(arr);
console.log(xj);
let array =[1,1,2,2,3,4,5,2];
array = [... new Set(array)];
console.log(array);
</script>
4 遍历
1.forEach()
2.for of
xj.forEach(function (value, key, set) {
console.log(value, key,set);
})
console.log("@@@@@@@@@");
for(const item of xj){
console.log(item);
}
5 利用set特性达到记录输入栏不重复
“blur”取消焦点
<input type="text" name="xj" />
<ul></ul>
let obj ={
data:new Set(),
keyword(word){
this.data.add(word);
},
show() {
let ul = document.querySelector("ul");
ul.innerHTML = "";
this.data.forEach(function (value) {
ul.innerHTML += `<li>${value}</li>`;
});
}
};
let input = document.querySelector("[name='xj']");
input.addEventListener("blur", function () {
obj.keyword(this.value);
obj.show();
});
6网站用户数据比较 :并集交集 差集
并集
let a= new Set([1,2,3,4,5]);
let b = new Set([4,5,6,2]);
console.log(new Set([...a, ...b]));
差集
let a= new Set([1,2,3,4,5]);
let b = new Set([4,5,6,2]);
// console.log(new Set([...a, ...b]));
console.log(
new Set([...a].filter(function (item) {
return !b.has(item);
})))
交集
let a= new Set([1,2,3,4,5]);
let b = new Set([4,5,6,2]);
// console.log(new Set([...a, ...b]));
console.log(
new Set([...a].filter(function (item) {
return b.has(item);
})))
4 WeakSet
不能有重复元素,元素需是引用类型
1.delete(),has(),
2.不可以遍历,因为他是弱引用,造成算法不准确。
3.例子:删除li项
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Title</title>
</head>
<body>
<!--<div></div>
<div></div>-->
<ul>
<li>刘兴加 <a href="javascript:;">x</a></li>
<li>刘兴 <a href="javascript:;">x</a></li>
<li>刘加 <a href="javascript:;">x</a></li>
</ul>
</body>
<style>
body{
padding: 200px;
}
li{
border: solid 2px orange;
padding: 4px;
margin: 4px;
}
a{
padding: 5px;
background: darkgreen;
color: white;
right: 3px;
text-decoration: none;
}
.remove{
background: #dddddd;
color: #34495e;
border: solid 2px #34495e;
}
</style>
<script>
/*let nodes = new WeakSet();
let divs = document.querySelectorAll("div");
divs.forEach(function (item) {
nodes.add(item);
});
nodes.delete(divs[0]);
console.log(nodes);
console.log("###########");*/
// let hd = {name:"lxj"};
// let edu = hd;
// console.log(edu);
// console.log("############");
// let set = new WeakSet();
// set.add(hd);
// hd = null;
// //edu = null;
// console.log(set);
class ToDo{
//新建一个类
constructor(){
this.items = document.querySelectorAll('ul>li');
// console.log(this.items);
this.lists = new WeakSet();
this.items.forEach(item =>{ this.lists.add(item);
});
//把li放进lists这个weakset中
console.log(this.lists);
}
run(){
this.addEvent();
//运行addevent函数
}
addEvent(){
this.items.forEach(item =>{
//this.item是li的对象,有三个,即三个item
let a = item.querySelector("a");
//选择li中的a,扔到a中
a.addEventListener("click", event => {
//给a添加监听事件,点击执行
const parentElement = event.target.parentElement;
//得到此a的父元素
console.log(parentElement);
if(this.lists.has(parentElement)){
//如果此a的父元素在页面li集合中
// alert(3);
parentElement.classList.add("remove");
this.lists.delete(parentElement);
//先添加父元素remove的class属性,再将此父元素从weakset中移除但其实未将其从其父节点删除
}else{
parentElement.classList.remove("remove");
this.lists.add(parentElement);
}
});
});
}
}
new ToDo().run();
//新建todo对象,并执行函数
</script>
</html>
5函数
1.函数定义方式:
不常用
let func = new Function("title","console.log(title)");
func("lxj");
常用:
function lxj(title) {
console.log(title);
}
lxj(22);
函数赋值给变量:
let lxj = function (title) {
console.log(title);
};
lxj(22);
在对象中:
let user = {
name:null,
setUsername : function(name){
this.name = name;
},
getUsername: function () {
return this.name;
},
};
user.setUsername("张三");
console.log("####"+user.getUsername());
或简写形式
setUsername(name){
this.name = name;
},
getUsername() {
return this.name;
},
2.函数创建后会被压入window对象中
window.func()可以执行。
但这并不合适,因为如果与window内的函数重名会覆盖其,影响window的函数的正常使用。
winidow.screenX,返回窗口左边距屏幕左边距离。
解决方法,将函数赋值给let变量,
let cms = function () {
console.log("222")
}
cms();
3函数最好编到类或模块中使用,不单独使用
4匿名函数与函数提升
1.一般函数定义放在调用后也可以执行,
但匿名函数不会有函数提升
hd();
let hd = function () {
console.log("222")
}
其实reduce()括号内的函数show不写名字一样调用,一般不会写名字,因为不会调用第二次。这就是匿名函数的用处。return arg.reduce(function (a,b)
function sum(...arg) {
return arg.reduce(function show(a,b) {
//return arg.reduce(function (a,b)
return a+b;
});
}
console.log(sum(1,3,4,5,1));
——————————————————————————————————————————————————————————————
setInterval的第一个参数就是匿名函数
var i= 0;
setInterval(function () {
console.log(++i);
},1000);
等于
var i= 0;
setInterval(xj,1000);
function xj() {
console.log(++i);
}
2函数是引用类型是对象,可以赋值给其他变量
3立即执行函数和作用域
用以下方法可以使得引入的js文件不与原本文件变量名冲突等,
5默认参数的排序例子,
1.默认参数放在后面,
2.若不传递参数就是升序,否则就是降序
<script>
function sortArray(array, type = "asc") {
return array.sort( (a,b)=> {type=="asc"?a-b:b-a;});
}
console.log(sortArray([1,4,2,7,4,7,3], "desc"));
</script>
————————————————————————————___——
6作为参数传递函数
function xj(a) {
return a>2;
}
let arr1 = [1,3,4,2,4,1,4].filter(xj);
console.log(arr1);
var i= 0;
setInterval(xj,1000);
function xj() {
console.log(++i);
}
7arguments接收多个实参,很神奇
形参没有写参数但在函数体中,arguments收集了所有 参数,但它并不是数组类型
function sum() {
return [...arguments].reduce((a,b)=> a+b);
}
console.log(sum(1,2,3,4,5,6,6));
以前常用这种方式,现在可以使用展开语法来代替
function sum(...s) {
return s.reduce((a,b)=> a+b);
}
console.log(sum(1,2,3,4,5,6,6));
8函数缩写形式
(参数)=>{函数体};
参数,胖箭头,函数体。
函数体只一行,不加return,不加花括号,不加分号。
let xj = [1,2,3,4,5,6].filter(val => val<4);
console.log(xj);
function sum(...s) {
return s.reduce((a,b)=> a+b);
}
console.log(sum(1,2,3,4,5,6,6));
8,递归
利用递归输出三角形。
function star(sum) {
return sum?document.write("*".repeat(sum)+"<br>")||star(--sum):"";
//document.write("*".repeat(sum)+"<br>")返回值是undefine
}
star(7);
9.回调函数是在其他函数中调用的函数。
let xj = [1,2,3,4];
function plus(val) {
val += 10;
return val;
}
xj = xj.map(plus);
console.table(xj);
10展开语法(收,展)
在数组中和函数的形参参数中使用,在形参中展开语法放最后
折扣例子:
function sum(discount = 0, ...price) {
console.log(price.reduce((a,b) => a+ b) * (1-discount));
}
sum( 0, 100,350, 540, 650, 230);
11.this指针,
1.对象方法中指向对象,普通函数指向window
2.对象方法中的函数指向winidow,若想在函数中使用this指向对象,
可先定义let This = this,在下面即可以使用。
还有如reduce(,,this),可在第三个参数中传入this,即可使用
3.箭头函数对this指针造成不同,在其中指向对象,不指向window。
I.button.onclick = () => console.log(this);
this是Dom
let Dom = {
site:"lxj",
bind: function () {
const button = document.querySelector("button");
//console.log(button);
/*button.addEventListener("click",function () {
})*/
button.onclick = () => console.log(this);
}
}
Dom.bind();
II.button.onclick = function () {
console.log(this);
}
this值是button
let Dom = {
site:"lxj",
bind: function () {
const button = document.querySelector("button");
//console.log(button);
/*button.addEventListener("click",function () {
})*/
button.onclick = function () {
console.log(this);
}
}
}
Dom.bind();
=======================
III.而当两者都要 使用时的解决方法
button.addEventListener("click",event =>{
console.log(event.target);
//button
console.log(this);
//Dom
})
event.target.innerHTML = this.site + event.target.innerHTML;即可在按钮文本前加入site值。
12call apply bind
一、意义:改变函数中this指向的对象。
1.
let lisi = {
name : "李四"
};
let wangwu = {
name : "王五"
};
function User(web, url) {
console.log(this.name + web + url);
}
User.call(lisi, "liuxingjia", "lxj.com");
User.apply(wangwu, ["liuxingjia", "lxj.com"]);
call、 bind、 apply 这三个函数的第一个参数都是this的指向对象,第二个参数差别就来了:
call 的参数是直接放进去的,第二第三第n个参数全都用逗号分隔,直接放到后面obj.myFun.call(db,‘江西’, …, ‘string’)。
apply的所有参数都必须放在一个数组里面传进去。
bind除了返回函数以外,它的参数和call 一样。
当然,三者的参数不限定是String 类型,允许是各种类型,包括函数,对象等等。
————————————————
版权声明:本文为CSDN博主「世平」的原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接及本声明。
原文链接:https://blog.csdn.net/weixin_42321292/article/details/82352997
2.
<button>
嘻嘻嘻
</button>
<button>
嘤嘤嘤
</button>
function show() {
alert(this.innerHTML);
}
let button = document.querySelectorAll("button");
// console.log(button);
button.forEach(item =>
{item.addEventListener("click", a => show.call(a.target))})
console.log(Math.max.apply(Math,[1,3,4]));
3.模拟服务器端和用户端使用call()函数。
function Request(){
this.get = function (params) {
let str = Object.keys(params)
.map(k => `${k} = ${params[k]}`).join("&");
let url = `https://houdunren.com/${this.url}?${str}`;
document.write(`${url} <br/>`);
};
}
console.log(Math.max.apply(Math,[1,3,4]));
function Article() {
this.url = "article/lists";
Request.call(this);
}
function User() {
this.url = "user/lists";
Request.call(this);
}
let user = new User();
user.get({id:2, role : "admister"});
let a = new Article();
a.get({id:1, cat : "three"});
4.bind用法,返回函数,所以要加括号才执行
function show() {
console.log(this.name);
}
let a = show.bind({name:"张三"})();
利用bind不立即执行特点,用来向函数中传递想要的对象。
document.querySelector("button").addEventListener(
"click",
function (event) {
document.write(this.url+event.target.innerHTML)
}.bind({url:"liuxigjia.com"})
5.运用的例子:
随机改变颜色使用bind
<body>
<h1>嘻嘻嘻fight!!!</h1>
</body>
<style>
body{
padding: 200px;
font-size: 50px ;
color: #dddddd;
font-weight: bold;
font-family: 手札体-简;
background-color: #34495e;
}
</style>
<script>
function Color(elem) {
this.elem = elem;
this.colors = ["#1abc9c","#f1c40f","#9b59b6","#f39c12","#123456"];
this.run = function () {
console.log(this);
console.log(this.elem);
console.log(this.colors.length);
setInterval(
function () {
let i = Math.floor(Math.random()*this.colors.length) ;
console.log(i +"@@@@@@@@");
this.elem.style.backgroundColor = this.colors[i];
}.bind(this),1000);
}
}
let obj = new Color(document.body);
console.log(document.body);
obj.run();
let h1 = new Color(document.querySelector("h1"));
h1.run();
</script>