数组中的innerHTML [重复]
Posted
技术标签:
【中文标题】数组中的innerHTML [重复]【英文标题】:innerHTML in an array [duplicate] 【发布时间】:2016-03-13 14:59:53 【问题描述】:我正在尝试制作画廊。
我在所有步骤中都成功了,除了最后一个,单击缩略图会将段落中的文本更改为我放入数组中的另一个文本。
当我在 for 循环中时,我希望在单击索引 2 的图像时显示索引 2 的文本。我似乎遵循了正确的语法,但段落仍然显示“未定义”因此。但是,当我选择一个索引时,就像我单击的任何图片一样,我想显示索引 3 的文本,它可以工作。
这是我的简化代码,应该允许我在单击段落时显示文本。如果你们不使用 jQuery,那就太棒了。谢谢大家!
<!DOCTYPE html>
<html>
<body>
<p class="demo">1</p>
<p class="demo">2</p>
<p class="demo">3</p>
<script>
var cars = ["Saab", "Volvo", "BMW"];
var para = document.getElementsByClassName("demo");
for (k=0;k<cars.length;k++)
para[k].onclick=function()
this.innerHTML = cars[k];
</script>
</body>
</html>
【问题讨论】:
问题可能是索引k
没有在您的for
循环中的循环之间得到保留。您需要使用闭包。
【参考方案1】:
这是 javascript 范围的问题。您的变量 k,请注意您每次如何增加它。当点击事件调用 onclick 时,无论您点击的是什么图片,k 都会以 3
作为其值。
你可以试试这个解决方法(注意我稍微清理了你的代码)
<!DOCTYPE html>
<html>
<body>
<p class="demo">1</p>
<p class="demo">2</p>
<p class="demo">3</p>
<script>
var cars = ["Saab", "Volvo", "BMW"];
var para = document.getElementsByClassName("demo");
for (k = 0; k < cars.length; k++)
(function (index)
para[index].onclick = function()
this.innerHTML = cars[index];
(k));
</script>
</body>
</html>
在这种情况下,每个值都由 k 组成一个单独的副本,这个副本在函数内部作为“索引”可用。
关于具体问题的更多信息,可以参考这个帖子:JavaScript closure inside loops – simple practical example
【讨论】:
完美!谢谢。这就是我要找的!尽管我是初学者,但我会尝试解密此代码,并且我不太了解您将函数放在括号之间的部分。 是的!!!!我现在明白了!并且能够将它应用到我的实际项目中(我在问题中输入的小代码就像尝试该技术的简单演示一样。)我将在此评论中附加哪些代码(如果可能,否则我将通过电子邮件发送)如果有兴趣。再次感谢大家!!!【参考方案2】:使用闭包:
<script>
var cars = ["Saab", "Volvo", "BMW"];
var para = document.getElementsByClassName("demo");
for (var k = 0; k < cars.length; k++)
(function (k)
para[k].onclick = function ()
this.innerHTML = cars[k];
(k));
</script>
小提琴:http://jsbin.com/zezuhitige
原因:
该值将始终是循环的最后一个值。所以当点击发生时你总会得到k = 3
,k
的值是在点击的时候执行的,也就是3
。闭包通过在赋值时正确执行值来防止这种情况发生。
【讨论】:
【参考方案3】:更灵活的做法是这样的:
<div id="container">
<p class="demo" data-car="Saab">1</p>
<p class="demo" data-car="Volvo">2</p>
<p class="demo" data-car="BMW">3</p>
</div>
JS:
document.getElementById('container').onclick = function(e)
e = e || window.event;
var target = e.srcElement || e.target;
while( target != this && !target.className.match(/\bdemo\b/))
target = target.parentNode;
if( target != this)
// target is now one of the .demo elements
target.innerHTML = target.getAttribute("data-car");
;
这会将数据本身与它所引用的元素一起放入,并且只附加一个事件侦听器而不是每辆车一个 - 在更大的应用程序中,您拥有的事件处理程序越少越好!
【讨论】:
【参考方案4】:查看 JS 闭包并尝试以下操作:
https://developer.mozilla.org/en-US/docs/Web/JavaScript/Closures
document.addEventListener("DOMContentLoaded", function(event)
var cars = ["Saab", "Volvo", "BMW"];
var para = document.getElementsByClassName("demo");
for (k=0;k<cars.length;k++)
var clojureCar = cars[k];
para[k].onclick=function()
this.innerHTML = clojureCar;
);
<!DOCTYPE html>
<html>
<body>
<p class="demo">1</p>
<p class="demo">2</p>
<p class="demo">3</p>
<script>
var cars = ["Saab", "Volvo", "BMW"];
var para = document.getElementsByClassName("demo");
for (k=0;k<cars.length;k++)
para[k].onclick=function()
this.innerHTML = cars[k];
</script>
</body>
</html>
【讨论】:
【参考方案5】:我认为添加这样的事件侦听器是一个好习惯。而且因为你的点击事件是在你的循环完成后执行的,所以它总是 3 是未定义的。
var cars = ["Saab", "Volvo", "BMW"];
var para = document.getElementsByClassName("demo");
for (k=0;k<cars.length;k++)
var div = para[k];
(function (i)
div.addEventListener('click', function() this.innerHTML = cars[i]; );
)(k);
【讨论】:
以上是关于数组中的innerHTML [重复]的主要内容,如果未能解决你的问题,请参考以下文章
语法中的 innerHTML 错误不起作用;未捕获的 TypeError:无法设置 null 的属性(设置“innerHTML”)[重复]