1)参数1(索引)如何知道是整数?
jQuery 传递一个整数。
2)函数如何知道增加索引?
回调不会递增index
,jQuery 方法会。
3)第二个参数(oldValue)如何知道保存属性的旧值(修改前)?
jQuery 通过它。
问题 1-3 的答案可能最好通过执行类似于以下操作的函数来理解$.attr
:
Array.prototype.each = function (f) {
var i;
for (i=0; i < this.length; ++i) {
f(i, this[i]);
}
};
['zero', 'one', 'two'].each(function (i,item) {console.log({i: item})});
f
是一个回调。each
负责迭代集合并调用f
每个索引和项目。相同的代码结构可用于函数:
/* Map each item in a sequence to something else,
* returning a new sequence of the new values.
*/
Array.prototype.map = function (f) {
var i, result = [];
for (i=0; i < this.length; ++i) {
result[i] = f(i, this[i]);
}
return result;
};
['zero', 'one', 'two'].map(function(i,item) {return item.length});
// result: [4, 3, 3]
/* Return a sequence of the items from this sequence
* for which 'keep' returns true.
*/
Array.prototype.filter = function (keep) {
var i, result = [];
for (i=0; i < this.length; ++i) {
if (keep(i, this[i])) {
result.push(this[i]);
}
}
return result;
};
['zero', 'one', 'two'].filter(function(i,item) {return item.length <= 3});
// result: ['one', 'two']
的实施mapconcat
,foldl
并foldr
留作练习。作为另一个练习map
,filter
根据each
.
请注意,这些函数仅用于说明回调如何工作。它们可能会导致生产代码出现问题。
4) 这是一个 jQuery 构造吗?一个 JSON 的东西?这个很酷。它有效,但是......这个“价值回调”到底是由什么组成的?
回调是 jQuery 广泛使用的一种通用技术。它们是函数式编程的关键特性,其中函数是可以像其他数据类型一样操作的数据。因此,您拥有将函数作为参数并可以返回函数的函数。在某些情况下,回调也称为“延续”,并构成延续传递风格( CPS ) 的基础。这对于异步函数调用[ 2 ](与同步调用相反,函数在计算完成之前返回)尤其重要,例如用于 Ajax 请求。要了解 CPS 的一些功能,请阅读“使用延续开发复杂的 Web 应用程序”。
另一方面,“值回调”中的“值”是,由于 JS 是一种动态类型语言(类型与数据相关联,而不是变量),形式参数可以绑定到任何类型的对象。然后,函数可以根据传递的内容而表现不同。有时这是通过检查参数的类型来实现的,这实际上是临时多态性(函数而不是语言必须处理调度)。然而,参数多态性或(失败)鸭子类型应该始终优先于检查参数类型。参数多态性是通过确保可以传递给给定函数的所有类型都支持相同的接口(方法名称、参数、前置条件、后置条件等)来实现的。例如,所有的序列类型都应该有一个length
属性并由整数索引;只要这一点成立,您就可以将自己的序列类型与许多采用数组的函数一起使用。
我不确定您所说的 JSON 是什么意思,但这可能不是通常的意思。JSON 是一种基于 JS 对象文字语法的受限版本的数据交换格式。示例代码或引用文本中的任何地方都没有涉及 JSON。