看JS,一直纠结于for循环事件绑定,我一直不理解,想找到一些解释,以下是个人研究一个下午后的一些见解,有不对的还望大神们指正,轻喷。在这里谢过啦。

首先,目的是做一个滑动切换图片的效果,上JS代码:

// 拿对象
// 获取所有的按钮div,返回一个数组
var barArr=document.getElementsByClassName("up_stript_div_bar")
//定义一个图片的数组
var imgSrcArr=new Array("images/视频.jpg","images/秒拍.jpg","images/综艺.jpg")
往后,一开始我是这样写的:“勤快写法”
barArr[0].onmouseover=function overIt() {
document.getElementById("imgBig").src=imgSrcArr[0]; }
barArr[1].onmouseover=function overIt() {
document.getElementById("imgBig").src=imgSrcArr[1];
}
barArr[2].onmouseover=function overIt() {
document.getElementById("imgBig").src=imgSrcArr[2];
}
发现是可以的; 然后,就想试一下for循环绑定,代码如下:
for(var i=0;i<barArr.length;i++){
barArr[i].onmouseover=function overIt() {
document.getElementById("imgBig").src=imgSrcArr[i];
} }
结果显示:undefined:1 Failed to load resource: the server responded with a status of 404 (Not Found)
当时我就好奇了,什么情况??
for循环理论上,是一种迭代偷懒的计数器,你给他设定范围,设定步长,他就做事。难道结果不是跟第一种如下一开始的一样么?
barArr[0].onmouseover=function overIt() {
document.getElementById("imgBig").src=imgSrcArr[0]; }
barArr[1].onmouseover=function overIt() {
document.getElementById("imgBig").src=imgSrcArr[1];
}
barArr[2].onmouseover=function overIt() {
document.getElementById("imgBig").src=imgSrcArr[2];
}
经过我的思考我发现了这点:
最上面这种全部列出来的“勤快写法”;大致可以看成是这样
[0]------[0]
[1]------[1]
[2]------[2]
而上面那个for循环的结果是什么呢?
我原以为也是这样,因为通过打印,发现,他是执行完0,1,2的过程的,难道不是左右都有,然后等待鼠标事件?
但其实应该只有一半!: 他是分两步来完成的:
第一:
[0]----
[1]---
[2]---
for循环结束,一切定格,它能做的就这么多啊 第二: 鼠标事件发生
[0或1或2] ------i
因为后一半要通过鼠标事件才可以显现,它是被好好的保护着的,一旦鼠标事件发生,好家伙,function部分醒过来了,手上拿着i,问i是多少,好的,i是3,于是,你到哪找3给它。于是就报错了。
它根本没有完成开头的“勤快写法的全部”,(for循环就是为了减少代码量的) 所以,问题在于,怎么把“勤快写法”给表现出来。做的事情不能少。 问题知道了,下面看怎么解决: 解决一:用另外一个跟随被点击对象的自定义属性来复制一份[0][1][2]
简单说,就是
被点的对象,都手持一个牌子,被点的时候,就告诉后面一个数组,牌子的标号。看代码:
for(var i=0;i<barArr.length;i++){
// console.log(i)
barArr[i].n=i;
barArr[i].onmouseover=function () {
console.log(i)
document.getElementById("imgBig").src=imgSrcArr[this.n]; }
}
变成了这样:
n
[0]--[0]---
[1]--[1]---
[2]--[2]---
鼠标点击时,i=3,但是要什么紧。又不根据i找,你点哪个,我把对应的n给你,因为复制好一份对应的n的一列。这个完成了操作,就跟映射列表一样,都对应好了。

解决二:
闭包:
这个是我自学的。
大概意思就是,函数包函数,这个在java里面是不允许的,一般是函数包一个函数的调用。
但有一条一样:就是如果一个函数的内在成员如果是被另一个函数引用的话,那他就不会被垃圾回收机制干掉(java和js都有垃圾回收机制)
一开始我是这样写的:想着闭包,干脆别那么麻烦,少些那个注释的两行:看代码:
for(var i=0;i<barArr.length;i++){
barArr[i].onmouseover=(function (i) {
// return function () {
document.getElementById("imgBig").src=imgSrcArr[i]
} //})(i) }
思考:那两条双斜杠的,少了会怎么样?

那是一个自执行函数,简单来说,这样(function(i){巴拉巴拉})(i),就是他可以自己自动执行,可以传参。
问题是,它到底是个什么过程?如下?
[0]--[0]
[1]--[1]
[2]--[2] 鼠标事 i=3
这个更有意思,我觉得,它是执行完,但都随后直接弹栈了。。。。。因为,它执行完了,根本不需要鼠标事件了。。。。

于是,闭包就来了
首先:它内部函数吊着外面的变量,他不会被回收
具体,我觉得是这样,它是真的完成了操作,也没借助额外的属性设置:
[0]--[0]
[1]--[1]
[2]--[2]
for循环结束,
i=3
鼠标事件,就跟一开头的“勤快写法一样” 所以,关键点在于闭包,它没弹栈。 总结:最先前的,直接写i的那种,鼠标事件之前,它完成了左边的赋值,右面没有,鼠标事件一发生,i的值是4
闭包:用的是它内部函数吊着外面的一个变量,它不弹栈。 今天研究了一个下午的成果,如上。 多谢学习给我带来快乐! 加油!


初学笔记之:Java_Script的for循环事件绑定的更多相关文章

  1. vuejs学习笔记(1)--属性,事件绑定,ajax

    属性 v-for 类似于angular中的 ng-repeat ,用于重复生成html片段: <ul id="box"> <li v-for="(v, ...

  2. vuejs学习笔记(2)--属性,事件绑定,ajax

    属性 v-for 类似于angular中的 ng-repeat ,用于重复生成html片段: <ul id="box"> <li v-for="(v, ...

  3. JQuery在循环中绑定事件的问题详解

    JQuery在循环中绑定事件的问题详解 有个页面上需要N个DOM,每个DOM里面的元素ID都要以数字结尾,比如说 ? 1 2 3 <input type="text" nam ...

  4. C++ STL初学笔记

    C++  STL初学笔记 更系统的版本见徐本柱的PPT set 在这儿:http://www.cnblogs.com/pdev/p/4035020.html #include <vector&g ...

  5. lufylegend库 鼠标事件 循环事件 键盘事件

    lufylegend库 鼠标事件 循环事件 键盘事件 <!DOCTYPE html> <html lang="en"> <head> <m ...

  6. 【python学习笔记】5.条件、循环和其他语句

    [python学习笔记]5.条件.循环和其他语句 print: 用来打印表达式,不管是字符串还是其他类型,都输出以字符串输出:可以通过逗号分隔输出多个表达式 import: 导入模块     impo ...

  7. 【Visual C++】游戏编程学习笔记之六:多背景循环动画

    本系列文章由@二货梦想家张程 所写,转载请注明出处. 本文章链接:http://blog.csdn.net/terence1212/article/details/44264153 作者:ZeeCod ...

  8. Python编程从入门到实践笔记——用户输入和while循环

    Python编程从入门到实践笔记——用户输入和while循环 #coding=utf-8 #函数input()让程序暂停运行,等待用户输入一些文本.得到用户的输入以后将其存储在一个变量中,方便后续使用 ...

  9. Spring 初学笔记

    Spring 初学笔记: https://blog.csdn.net/weixin_35909255/article/category/7470388

随机推荐

  1. html5+hbuilder+夜神模拟器+webview

    HTML5 Plus应用概述 首先新建一个移动App项目,文件-->新建-->移动APP HTML5 Plus移动App,简称5+App,是一种基于HTML.JS.CSS编写的运行于手机端 ...

  2. 移动开发day2_css预处理器_flex布局

    css预处理器 一种技术,可以提高编写css代码的技术而已. 有3种预处理器常见 less sass stylues less使用流程 编写符合less语法的less文件 使用工具 将less编译成 ...

  3. Python认识到放弃

    基础入门 计算机硬件基础 变量 数据类型 基本运算符 变量常量 流程控制 数据类型 数字,字符串,列表 元组,字典,集合 字符编码 python2 python3 文件处理 文件读写 指针移动 函数 ...

  4. 吐血记录微信小程序授权获取Unionid及linux下使用bouncycastle解密用户数据 遇到的坑

    背景 公司小程序上线了,发现系统无法拿到一些用户的UniondID.但是上线前的测试一切都是正常的. 坑1 经排查,发现一些用户通过下面的接口无法得到unionid https://api.weixi ...

  5. apply,all,bind的区别

    这三个都是用来改变this指向的 call() 和apply()的第一个参数相同,就是指定的对象.这个对象就是该函数的执行上下文.call()和apply()的区别就在于,两者接收的参数不一样.cal ...

  6. Linux-Shell编程之判断文件类型

    前言 如需使用本博文源码或者撰写文章,请注明博文来源:https://www.cnblogs.com/johnnyzen/p/10534386.html,劳动所得,侵权必究. 题目 設計一個shell ...

  7. hibernate之一级缓存

    缓存目的:提高效率. sql语句与数据库交互,返回数据组装成对象存入session缓存中.程序查询时,优先访问缓存中是否存在id相同对象. hibernate中session缓存(一级缓存)存在

  8. hibernate之一对多,多对一

    配置文件 <!--一对多--><!--name:集合属性名字 column:外键列名 class:与它相关的对象的完整列名 cascade:级联操作:分3种 save-update: ...

  9. java控制多线程同时写一个文件

    最近出现一个需求,大体要做的就是控制多线程同时操作一个文件.当时第一个反应是不要用synchronized,太low了,然后我就使用了读写锁ReentrantReadWriteLock,然后写完静下来 ...

  10. 如何用java实现一个p2p种子搜索(1)-概念

    前言 说句大实话,网上介绍怎么用java实现p2p种子的搜索这种资料不是特别多,大部分都是python的,用python的话就会简单很多,它里面有很多简单方便的包,libtorrent等等,当然你用这 ...