2010-10-12 30 views
39

John Resig, şık bir Sınıf işlevi yazdı, havalı. Ben neler olduğunu anlamaya çalışıyorum ve hemen hemen her şey tek bir satır hariç anladım:Garip JavaScript deyim - "/xyz/.test(function(){xyz;})" ne yapar?

fnTest = /xyz/.test(function() {xyz;}) ? /\b_super\b/ : /.*/; 

birkaç nokta hemen akla atlamak ilk xyz bir değişken olarak hiçbir zaman başlatıldı; Peki neden bu işe yarar? İkincisi, neden hiçbir şey döndürmeyen bir şeye karşı (iade ifadesi yok) /xyz/ test ediliyor. Javascript'in bazı şık özellikleri olmadıkça habersiz olduğumdan (ki mümkünse, JS'de kendimi oldukça iyi hissediyorum ve karşılaştığım kodun çoğunu yorumlayabilirim, ancak, aynı Mt üzerinde olacağım anlamına gelmez) John Resig'in eve çağırdığı Everest büyüklüğünde dağ.

(function() { 
    var initializing = false, fnTest = /xyz/.test(function(){xyz;}) ? /\b_super\b/ : /.*/; 

    // The base Class implementation (does nothing) 
    this.Class = function(){}; 

    // Create a new Class that inherits from this class 
    Class.extend = function(prop) { 
    var _super = this.prototype; 

    // Instantiate a base class (but only create the instance, 
    // don't run the init constructor) 
    initializing = true; 
    var prototype = new this(); 
    initializing = false; 

    // Copy the properties over onto the new prototype 
    for (var name in prop) { 
     // Check if we're overwriting an existing function 
     prototype[name] = typeof prop[name] == "function" && 
     typeof _super[name] == "function" && fnTest.test(prop[name]) ? 
     (function(name, fn){ 
      return function() { 
      var tmp = this._super; 

      // Add a new ._super() method that is the same method 
      // but on the super-class 
      this._super = _super[name]; 

      // The method only need to be bound temporarily, so we 
      // remove it when we're done executing 
      var ret = fn.apply(this, arguments);  
      this._super = tmp; 

      return ret; 
      }; 
     })(name, prop[name]) : 
     prop[name]; 
    } 

    // The dummy class constructor 
    function Class() { 
     // All construction is actually done in the init method 
     if (!initializing && this.init) 
     this.init.apply(this, arguments); 
    } 

    // Populate our constructed prototype object 
    Class.prototype = prototype; 

    // Enforce the constructor to be what we expect 
    Class.constructor = Class; 

    // And make this class extendable 
    Class.extend = arguments.callee; 

    return Class; 
    }; 

})(); 
+1

.. okuyucu (in) akıl kontrolü? :) – mykhal

+0

.. hmm ... etiketlerinde kodu çevreledim, neden bu kadar kasaplık yaptığını merak ediyorum (not > .. < Oy vermem gerektiğini düşündüğüm şeyi düşünmüyorum, bugün benim günüm değil. – Akidi

cevap

49

O "işlevi ayrıştırma" çalışıp çalışmadığını kontrol etmek hızlı bir & kirli yolu adildir: meraklı olanlar için

, burada john resigs sitesinden John Resig Simple Javascript Inheritance tam düzenlenmemiş kodudur.

RegExp.prototype.test yöntemi argümanı alır ve String'e dönüştürür, işlevin içindeki xyz referansı hiçbir zaman değerlendirilmez.

Bunu neden kontrol etmek zorundasınız?

Function.prototype.toString yöntem bir fonksiyonun bir uygulaması bağımlı temsilini döndürür ve bazı uygulama, örneğin, eski Safari sürümleri, Mobil Opera ve bazı Blackberry tarayıcılarda, aslında yararlı bir şey döndürmez çünkü.

+0

xyz anonim işlev cisimciği gereksiz mi? – mykhal

+1

@mykhal, 'xyz ', aslında * fonksiyon decompilasyonunun * düzgün çalıştığını bilmek için aradığınız şeydir. fonksiyonun gövdesini içerir ... – CMS

+0

@CMS yep, nihayet bir süre sonra aldım ..) – mykhal