这是我的学校项目到目前为止的代码(使用 Murach的JavaScript和Ray Harris的DOM脚本)。本章仅涉及阵列,不包括原型,但我想根据互联网教程和参考资料进行试用:
/*
Operation
This application stores the last name, first name, and score for
one or more students and it calculates the average score for all of the scores
that have been entered. When the user clicks on the Clear button, this
application clears the score data from this application. When the user clicks
on the Sort button, this application sorts the data in alphabetical order by
last name.
Specifications
The program should use one or more arrays to store the data.
Assume that the user will enter valid data.
*/
var $ = function (id)
{
return document.getElementById(id);
}
/*
Array prototype object extension for averaging the contents
"Adding a method to the built-in Array object to extract the average
of any numerical values stored in the array is therefore a useful
addition to that object." http://javascript.about.com/library/blaravg.htm
*/
Array.prototype.average = function ()
{
var avg = 0;
var count = 0;
for (var i = 0; i<this.length; i++)
{
//never gets here:
alert(i + ": " + this[i]);
var e = +this[i];
if(!e && this[i] !== 0 && this[i] !== '0')
{
e--;
}
if (this[i] == e)
{
avg += e;
count++;
}
}
return avg / count;
}
var addScore = function ()
{
studentScores[$('last_name').value + ', ' + $('first_name').value] = $('score').value;
update();
}
var clearScore = function ()
{
for (var i in studentScores)
{
studentScores[i] = '';
}
update();
}
var sortScore = function ()
{
scores.sort();
update();
}
var update = function ()
{
var result = '';
for (var i in studentScores)
{
result += (i + ': ' + studentScores[i] + '\n');
}
$('scores').value = result;
$('average_score').value = studentScores.average().toFixed(1);
}
window.onload = function ()
{
//a variable is initialized inside a function without var, it will have a global scope:
studentScores = [];
$('add_button').onclick = addScore;
$('sort_button').onclick = sortScore;
$('clear_button').onclick = clearScore;
$('last_name').focus();
}
当代码进入“update()”函数(“addScore()”函数的结尾)并访问数组时, 它将原型中的“文字”代码填充到文本区域(并且无法在下一行找到平均值):
我没有足够的回复点来发布图片,但这是我的输出(Chrome JS控制台中没有错误):
lowe, doug: 82
average: function ()
{
var avg = 0;
var count = 0;
for (var i = 0; i<this.length; i++)
{
//never gets here:
alert(i + ": " + this[i]);
var e = +this[i];
if(!e && this[i] !== 0 && this[i] !== '0')
{
e--;
}
if (this[i] == e)
{
avg += e;
count++;
}
}
return avg / count;
}
任何帮助表示欢迎(欢迎最佳做法或算法建议)
答案 0 :(得分:1)
这很简单:Do not use for…in
enumerations for looping Arrays!您可以在clearScore
和update
函数中执行此操作。
for (var prop in obj)
遍历所有[可枚举]属性,包括从Array.prototype
继承的属性(至少对于Array对象)。 for (var i=0; i<array.length; i++)
循环不会出现这个问题。
答案 1 :(得分:1)
改变这个:
studentScores = []
到此:
studentScores = {}
...这样你就可以使用Object而不是Array。
for
中的average()
循环只是迭代数字索引而不是您创建的非数字键。
将您的average()
方法设置为与其他方法一样的独立功能,并将studentScores
传递给它以计算平均值,然后使用for-in
代替for
。< / p>
答案 2 :(得分:0)
您必须决定studentScores是否为数组(即,整数用于访问存储的数据)或Object / Associative Array(字符串用于设置/获取元素)。
如果你想使用学生的名字作为关键,你应该将studentScores声明为一个对象,并且你的'普通'方法必须添加到Object原型中(我不推荐)。
使用代码的当前状态,您偶然发现一个数组也是一个对象,并且可以像任何其他对象一样附加任意属性。您已按名称添加了属性,但在平均方法中,您尝试访问基于数字的索引。但这不是你要添加的数据存储的地方。
> a = [];
[]
> a['foo'] = 'bar';
'bar'
> a.length
0
> a[3] = 0;
0
> a.length
4