![](/img/trans.png)
[英]Why is the 'this' keyword required to call an extension method from within the extended class
[英]Why do we have to explicitly specify “this” when invoking an extension method from within a method of a class being extended?
public class StoreController : Controller
{
public string Index()
{
// implicitly specified instance does not work
//return GetMemberName();
// must specify this explicitly
return this.GetMemberName();
}
}
public static class Utilities
{
public static string GetMemberName(this Controller caller,
[CallerMemberName] string memberName = "")
{
return caller.GetType().FullName + "." + memberName;
}
}
從擴展的類的方法中調用擴展方法時,為什么必須顯式指定this
?
在我的思維模型中,例如,當我們初始化字段時,通常可以忽略this
。
從技術上講,擴展方法不是您的類所附加的方法。
yourClass.ExtensionMethod()
與yourClass.ClassMethod()
。
基本上,您正在做的事情是獲得一種方便的方法:
ExtensionMethod(YourClass yourClass) {
//do something
return yourClass;
}
這就是我對擴展方法的理解。 這是一種針對無法更改的類調用方法的便捷方法。 所以,這就是為什么不能沒有this.
就不能調用它的原因this.
這不是一個類方法。
擴展方法只是調用靜態方法的語法糖。 這行代碼return this.GetMemberName();
實際上轉換為對靜態方法(如Utilities.GetMemberName(this);
的調用Utilities.GetMemberName(this);
正如你所看到的,你必須發送this
到靜態方法,這就是為什么你需要的原因, this
關鍵字。
如果沒有出席決定這個問題的設計委員會會議,就很難說為什么會這樣。
在本文中,我在與特定對象實例相關的函數意義上使用方法或實例方法,而在數學意義上使用函數。 一個函數接收多個參數並創建一個結果(可能無效)
如果我們不考慮因為要調用的實際函數是在運行時確定而更復雜的虛擬方法,則任何方法調用和所有方法調用都是語法糖。 如果我們在下面定義了兩種方法
internal static class Extensions {
public static string FooEx(this MyClass self){
return self.ToString();
}
}
internal class MyClass {
public string Bar(){
var s1 = Foo();
var s2 = this.FooEx();
}
private string Foo(){
return ToString();
}
}
然后將兩者都轉換為函數調用,在這兩種情況下,第一個(也是唯一一個)參數將是this
標識的對象。 如果對此不確定,請查看為實例方法進行的任何調用所產生的IL,與代碼中的聲明相比,您會發現還有一個額外的參數。 此參數是this
引用, 始終作為第一個參數傳遞給實例方法。
因此,對於實例方法,編譯器仍然需要確定將哪個對象作為函數的第一個參數傳遞。 也就是說它有,如果你沒有調用的擴展方法做同樣 this
也意味着不能成為真正的原因,你必須使用this
在擴展方法的前面。
在Marvin的編譯器中,在Mono編譯器的基礎上構建的編譯器,我不得不對C#使用擴展方法做類似的技巧,並想知道為什么規范要求使用this
。真正的原因是編譯器強制您在擴展之前使用this
方法是,規格說明是這樣的。 做出該決定的原因是需要@EricLippert這樣的人的注意,他們在決定該要求時可能會在哪里
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.