关于js中回调函数的问题

<!DOCTYPE html>
<html>
	<head>
		<meta charset="utf-8">
		<title></title>
		<style type="text/css">
			button{
				outline: none;
				width: 120px;
				height: 40px;
				font:22px/40px Arial;
				background: red;
				color: white;
			}
		</style>
	</head>
	<body>
		<div id="buttons">
			<button><input type="checkbox" disabled>苹果</button>
			<button><input type="checkbox" disabled>香蕉</button>
			<button><input type="checkbox" disabled>草莓</button>
			<button><input type="checkbox" disabled>蓝莓</button>
			<button><input type="checkbox" disabled>榴莲</button>
			<button><input type="checkbox" disabled>西瓜</button>
			<button><input type="checkbox" disabled>芒果</button>
			<button><input type="checkbox" disabled>柠檬</button>
		</div>
	</body>
	<script type="text/javascript">
		const allButtons=document.querySelectorAll('#buttons>button')
		for(var i =0;i < allButtons.length;i +=1){
			allButtons[i].addEventListener('click',function(evt){
				var checkbox=evt.target.firstChild
				checkbox.checked=!checkbox.checked
				evt.target.style.backgroundColor=
				checkbox.checked? 'green' : 'red'
			})
		}
	</script>
</html>

代码如上所示,呈现的效果很简单,就是8个红色方框,点击以后变绿,然后再点击就恢复红色,点击后除了颜色的变化外方框里也会有勾选和取消的效果,如果for循环那里i使用let来定义,就不需要回调,但是这里使用回调只是为了学习

我有两个问题想要问下

第一:allButtons[i].addEventListener('click',function(evt)这里,实际上i的值已经变成8了,为什么还能有事件监听呢?这里for循环了8次,从0到7,我理解的是llButtons[i].addEventListener('click',function(evt)这个语句肯定也执行了8次,虽然function没有执行,但是事件监听是执行了的,是这样的嘛?

第二:当我们点击某个窗口的时候,这个evt参数会接收浏览器传过来的值,这个时候这个function函数是在哪个监听事件里执行的呢?另外如果function函数本来就有其他的值要传进来,又该怎么写呢?请知道的告诉下,谢谢

第一个是闭包问题  

用立即执行函数包一下

(function (i) {

      allButtons[i].addEventListener('click', function (evt) {

        var checkbox = evt.target.firstChild

        checkbox.checked = !checkbox.checked

        evt.target.style.backgroundColor =

          checkbox.checked ? 'green' : 'red'

      })

    })(i)

一个事件监听分为“绑定事件”和“触发事件”两个步骤。
在代码执行addEventListener时进行的是“绑定事件”的操作,只是把function函数与allButtons[i]元素的click事件进行关联。这时function函数不执行。
在对元素绑定了事件之后,当用户对元素点击操作(对于click事件)才进行“触发事件”的操作,这时与元素click事件关联的函数才执行。
 

1. allButtons.length=8, i<allButtons.length, 即i<8, 执行i+=1。若i=8,则不执行for循环了,因此不会执行下面的监听及函数。i=7时,执行i+=1和下面的监听及函数 。

2. 只有点击对应的button才会触发对应的监听和函数。如果函数要接收到参数的话,必然要有输入才能获取,这个输入可以是固定的(事先写好的),也可以是不固定的(动态输入的,比如input文本框)。