簡體   English   中英

JavaScript擴展類型返回

[英]JavaScript extending types return

我實際上在研究Crockford的Javascript:好的部分 我是JavaScript的新手,所以我很難理解這段代碼是如何工作的:

Function.prototype.method = function (name, func) {
    this.prototype[name] = func;
    return this;
};

這就是我的想法:

作為一個方法(一個對象內部的函數), this指向Function對象,但為什么需要返回該對象,因為我從方法內部訪問它? 如果我是對的, this是一個參考,而不是本地副本,所以:

Function.prototype.method = function (name, func) {
    this.prototype[name] = func;
};

應該也可以。

另一方面,在JavaScript中,沒有return語句的函數返回undefined並將其分配給Function.prototype.method

問題

歸還this什么意義?


工作示例#1

Function.prototype.method = function (name, func) {
    this.prototype[name] = func;
    return this;
};
var add = function(a, b) {
    return a+b;
};

Function.method('add', add);
var f = function() {};

print(f.add(1,2));

Number.method('integer', function () {
        return Math[this < 0 ? 'ceil' : 'floor'](this);
        });

print((-10/3).integer());

輸出:

-3 3


工作實例#2

Function.prototype.method = function (name, func) {
    this.prototype[name] = func;
};

var add = function(a, b) {
    return a+b;
};

Function.method('add', add);
var f = function() {};

print(f.add(1,2));

Number.method('integer', function () {
        return Math[this < 0 ? 'ceil' : 'floor'](this);
        });

print((-10/3).integer());

輸出:

-3 3

今天下午我已經發了一封電子郵件給道格拉斯克羅克福德這個問題,他的答復是:

F.method的(a)。方法(b)中。方法(c)中

我不是在開玩笑。 這是他寫的唯一的東西。

無論如何,我對他(隱秘)答案的個人解釋是鏈式方法創建

Function.prototype.method = function (name, func) {
    this.prototype[name] = func;
    return this; //This returns the same Function object into the chain below
};

var add = function (a, b) { return a+b; };
var sub = function (a, b) { return a-b; };
var mul = function (a, b) { return a*b; };
var div = function (a, b) { return a/b; };

Function.method('add', add).method('sub', sub).method('mul', mul).method('div', div);

也就是說,而不是在創建時使用一個線新的方法,可以重新申請在此前,返回對象鏈中的下一個方法Function

在這個例子中,鏈從左到右

|Function|--method-->|add|--returns-->|Function|--method-->|sub|--returns-->|Function|--method-->|mul|--returns-->|Function|--method-->|div|-->returns-->|Function|

讓我試着解釋一下。 我沒有看過那本書,但道格拉斯·克羅克福德的JavaScript中經典繼承有一個重要的句子,與關於Function.prototype.method的例子有關:

它返回這個。 當我編寫一個不需要返回值的方法時,我通常會返回它。 它允許級聯式編程。

實際上我對這個術語並不熟悉,我認為眾所周知的術語是“ Fluent Interface ”或“Method Chaining”,閱讀wiki頁面,有不同語言的例子,所以你會理解它。

PS。 @Gianluca Bargelli以這種方式提供使用Function.prototype.method的例子有點快,所以我不在我的回答中發布它

ADDON:如何根據您的示例使用它:

Function.prototype.method = function (name, func) {
    this.prototype[name] = func;
    return this;
}

Number.method('integer', function () {  // you add 'integer' method
        return Math[this < 0 ? 'ceil' : 'floor'](this);
        })
      .method('square', function () {  // you add 'square' method with help of chaining
        return this * this;
        });

console.info( (-10/3).integer().square() ); // <- again chaining in action

你看,integer()返回Number對象,所以你可以調用另一個方法,而不是寫:

var a = (-10/3).integer();
console.info( a.square() ); 

關於我使用它的方式很少,大多數時候我更喜歡寫“每個方法 - 帶縮進的新行,對我來說這種方式更具可讀性:

Function.method('add', add)
        .method('sub', sub)
        .method('mul', mul)
        .method('div', div);

通過這種方式,我看到了我的起點,“新行/縮進”告訴我,我仍然會修改該對象。 將它與長線比較:

Function.method('add', add).method('sub', sub).method('mul', mul).method('div', div);

或典型的方法:

Function.method('add', add);
Function.method('sub', sub);
Function.method('mul', mul);
Function.method('div', div);

ADDON2:通常我在使用實體時使用這種方法(Fluent接口模式),例如Java代碼:

public class Person {
  private String name;
  private int age;
  ..

  public String getName() {
    return this.name;
  }

  public Person setName( String newName ) {
    this.name = newName;
    return this;
  }

  public int getAge() {
    return this.age;
  }

  public Person setAge( int newAge ) {
    this.age = newAge;
    return this;
  }

  ..
}

它允許我以簡單的方式構造Person對象:

Person person = new Person().setName("Leo").setAge(20);

有些人使它有點不同,他們增加新的方法來set / get ,並把它with

public class Person {
  private String name;
  private int age;
  ..

  public String getName() {
    return this.name;
  }

  public void setName( String newName ) {
    this.name = newName;
  }

  public Person withName( String newName ) {
    this.setName( newName ); // or this.name = newName; up to you
    return this;
  }

  public int getAge() {
    return this.age;
  }

  public void setAge( int newAge ) {
    this.age = newAge;
  }

  public Person withAge( int newAge ) {
    this.setAge( newAge ); // or this.age = newAge; up to you
    return this;
  }
  ..
}

現在我的上一個例子看起來像:

Person person = new Person().withName("Leo").withAge(20);

這樣我們就不會改變set方法的含義(我的意思是我們不會增強它,因此它可以像大多數開發人員所期望的那樣工作......至少人們不希望set方法可以返回任何東西;))。 關於這些特殊方法的一個有趣的事情 - 它們可以放棄自我記錄,但是當你使用它們時它們提高了可讀性(比如在創建Person例子中, withName很好地告訴我們到底在做什么......

閱讀更多:
FluentInterface - Martin Fowler對該模式的描述
PHP中的流暢接口
每周源代碼14 - 流利的界面版 - 對我來說簡短而且足以看到利弊(以及其他資源的鏈接)

我不明白你的要求,但是如果你不返回任何東西,你將不會給Function.prototype.method分配任何東西,這樣的句子會讓那句無用嗎?

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM