价值,原型和财产的差异

好! 首先,这个问题来自一个在jQuery世界中挖掘得太深(而且可能会迷路)的人。

在我的研究中,我发现jquery的主要模式是这样的(如果需要更正wellcomed):

(function (window, undefined) { jQuery = function (arg) { // The jQuery object is actually just the init constructor 'enhanced' return new jQuery.fn.init(arg); }, jQuery.fn = jQuery.prototype = { constructor: jQuery, init: function (selector, context, rootjQuery) { // get the selected DOM el. // and returns an array }, method: function () { doSomeThing(); return this; }, method2: function () { doSomeThing(); return this;, method3: function () { doSomeThing(); return this; }; jQuery.fn.init.prototype = jQuery.fn; jQuery.extend = jQuery.fn.extend = function () { //defines the extend method }; // extends the jQuery function and adds some static methods jQuery.extend({ method: function () {} }) }) 

$初始化jQuery.prototype.init启动并返回一组元素。 但我不明白它是如何添加像.css.hide等jQuery方法。 到这个数组。

我得到的静态方法。 但无法得到它如何返回和所有这些方法的元素数组。

我也不喜欢那种模式。 他们有一个init函数,它是所有jQuery实例的构造函数 – jQuery函数本身仅仅是用new对象来创build对象:

 function jQuery(…) { return new init(…); } 

然后,他们将这些实例的方法添加到init.prototype对象中。 该对象在jQuery.fn作为接口公开。 另外,他们将jQuery函数的prototype属性设置为该对象 – 对于那些不使用fn属性的人。 现在你有

 jQuery.prototype = jQuery.fn = […]init.prototype 

但是他们也做了两件怪事:

  • 覆盖原型对象的constructor属性,将其设置为jQuery函数
  • 公开jQuery.fn上的init函数 – 它自己的原型。 这可能允许扩展$ .fn.init函数 ,但是非常混乱

我认为他们需要/想要做所有这些以防万一,但是他们的代码是一团糟 – 从对象文字开始,然后分配init原型。

如果将API视为外部方法集合,并将jQuery函数作为包装,则更容易进行消化。

它基本上是这样构造的:

 function a() { return new b();} a.prototype.method = function() { return this; } function b() {} b.prototype = a.prototype; 

除了ajQuerybjQuery.prototype.init

我确定Resig有他将api构造函数放在init原型中的原因,但我看不到它们。 Bergi提到的另外一些奇怪的东西:

1)模式需要从jQuery.fn.init.prototypejQuery.prototype的引用副本,允许一个奇怪的无限循环:

 var $body = new $.fn.init.prototype.init.prototype.init.prototype.init('body'); 

2)每个jQuery集合实际上都是jQuery.fn.init一个实例,但是由于它们引用了同一个原型对象,它使我们“想”这个集合是jQuery一个实例。 你可以像这样做同样的魔法:

 function a(){} function b(){} a.prototype = b.prototype; console.log( new b instanceof a); // true console.log( new a instanceof b); // true 

旁注:我亲自使用了以下类似结果的构造函数模式,没有奇怪:

 var a = function(arg) { if (!(this instanceof a)) { return new a(arg); } }; a.prototype.method = function(){ return this; };