4

所以我有一个难题,希望有人已经掌握了答案。阅读 jQuery 源代码,我还没有理解这里到底发生了什么。

 $('#div')      //returns a jQuery object
 $( $('#div') ) // returns an identical jQuery object
 $( $( $( $( $( $('#div') ) ) ) ) ) // returns the same idential object

我在插件开发中遇到过我不知道需要一个 sting 选择器或 jQuery 对象的实例。在这些情况下,我只是将选择器或 jQuery 对象传递给 jQuery,这样就可以保证得到我想要的 jQuery 对象。效果很好,但感觉太神奇了。当我这样做时,到底发生了什么?有没有更好的办法?

4

2 回答 2

1

基本我认为在函数中$(...)存在一些基本情况。

  • 在 Arg 是 String 类型中,传递 this 并找到或创建 HTML Dom 元素,然后将其封装到 JQuery 对象中。
  • 在 Arg 是 HTML Dom 类型中,将对象封装成 JQuery 对象
  • 在 Arg 是 JQuery 对象中,按原样返回它

但实际上存在更多的情况,并且在此之前进行了大量的调试和错误检查。

在http://jsapi.info/jquery/1.8.0/jQuery.fn.init查看更多信息 我可以从代码中看到什么,如果我们有的话。

var x = $('#div');
var y = $(x);

x和的内容y相等,但记忆的xy不相等。

假设我们有:

class $ {
  var x;
  $($ t) {
    this.x = t.x
  }
}

如果我们都称$这将具有相同的内在价值,但实际上与两个不同的对象不同,这将是可行的。

于 2012-09-19T20:48:13.257 回答
1

在回答这个问题之前,需要了解 $(...) 返回一个具有类似数组属性的特殊对象。从文档中:

jQuery 工厂函数 $() 返回一个 jQuery 对象,该对象具有数组的许多属性(长度、[] 数组访问运算符等),但与数组不完全相同,缺少数组的一些内置属性-in 方法(例如 .pop() 和 .reverse())。

所以,这就是发生的事情。

  1. 无论选择器的类型如何,new jQuery.fn.init( selector, context, rootjQuery );都会调用它,因此会创建一个新对象,并在此init()构造函数中设置其属性。

  2. $(...) 的参数经过检查是否为空、DOMElement、字符串或函数(通过 isFunction)

所有检查均失败,最后调用以下代码。

if (selector.selector !== undefined ) {
    this.selector = selector.selector;
    this.context = selector.context;
}
return jQuery.makeArray( selector, this );

this.length函数 makeArray() 通过简单地设置属性将提供的选择器转换为类似数组的对象,this.ret[0]=..., this.ret[1]=...这样它就“感觉”像一个数组,而它仍然是一个基于 jQuery 原型(又名$.fn)的对象。请记住,this上面的代码只是原型中的一个全新对象$.fn。此外,.selector属性.context从原始复制到此。

重要的是要注意,例如.prevObject属性将丢失,但可能会根据方法链接添加一个新属性。

总而言之,这需要时间和内存,简单地检查.selector何时有人可能将 jQuery 对象传递到您的插件中可能是有意义的。另一方面,与原始实例具有相同行为的新实例可能会有所帮助。

于 2012-09-19T21:56:43.927 回答