2011-12-26 108 views
3

考慮:d成員函數屬性

class B 
{ 
public: 
    int i = 4; 
} 

class A 
{ 
public: 
    B b; 

    this() 
    { 
     b = new B; 
    } 

    ref B f() 
    { 
     return b; 
    } 
} 

裁判存儲類中的成員函數f的前面是多餘的嗎? Class對象始終按引用傳遞,因此返回Bref B是否等同?

第二:pure會員功能?純函數只返回依賴於參數的東西。因此,它不應該依賴於該類的任何數據成員,因爲即使傳入了相同的參數,它們也可能會更改該函數的輸出。因此,pure成員函數因此也是一個static成員函數? (反過來也許不對)

第三:const和不可變成員類有什麼區別?區分不可變和const類對象的成員函數調用?在語義上,它是平等的,我們不能改變這兩個屬性的數據成員,對吧?

第四:我應該添加儘可能多的功能屬性嗎?像pureconstimmutable,nothrowfinal


真棒,剛發現這工作:

inout(B) f() inout 
{ 
    return b; 
} 

回答

5

ref B f()是一個通過引用返回B的函數。 B是類參考。 Ergo,它通過引用返回一個類的引用。這不是d廢話,因爲類引用可以反彈:

auto a = new A; 
a.f() = new B; // rebinds a.b, possible due to return by ref 

同樣,你也可以有指向類引用在d:

class A 
{ 
    B b; 

    /* ... */ 

    B* f() 
    { 
     return &b; 
    } 
} 

auto a = new A; 
B* b = a.f(); // pointer to reference to instance of class B 
*b = new B; // updates a.b 

對於pure成員函數中,隱含this參考參數就是這樣 - 另一個參數。它被認爲是輸入的一部分。與同一個this對象和相同的常規參數一樣,輸出仍然總是相同。


隨着const成員函數,你不知道,如果this對象是可變的或不可變的。它可以是 - const成員函數承諾不會改變它。使用immutable成員函數時,this對象始終是不可變的。因此this引用可以作爲不可變參數傳遞給另一個函數,或者分配給不可變變量。


當決定何時去關心constimmutablepurenothrow,你必須考慮你是否真正在客戶端代碼需要這些不同的擔保。如果你正在編寫一個通用的庫,你可能不知道這個,所以在這種情況下,最好提供儘可能多的保證。

對於final,情況有爭議。如果您不希望客戶端代碼意外覆蓋無效的重載函數,或者您不希望重寫函數,或者希望編譯器有更多機會優化對該函數的調用,請使用它。不覆蓋任何函數的最終函數(使用override)並且不實現任何接口函數不一定是虛函數,從而減少通話開銷。

+0

在完美模塊化代碼的情況下,所有的功能將是純粹的? – 2011-12-26 18:17:13

+1

@Daevius,你不能從純函數中調用不純的函數。這排除了系統調用以及取決於它們的一切。我認爲,通過這個衡量標準,你的代碼永遠不會「完美」模塊化,它總是依賴於某種單一的行爲。 – 2011-12-26 19:05:10

+0

有關'pure'的更多信息,請參閱以下最近的問題:http://stackoverflow.com/questions/8572399/how-is-this-pure-function-able-to-modify-non-private-state – 2011-12-27 00:32:29

2

於是久違B和REF B等同?

ref使得該函數返回一個左值,因此允許:

auto a = new A; 
auto b = new B; 
b.i = 55; 
a.f() = b; 
writeln(a.b.i); // 55 

pure成員函數?

成員函數可以視爲一個自由函數,將實例作爲參數之一。

class A { pure void f(int others) immutable; } 
<=> 
    class A { ... } 
    pure void f(immutable(A) this, int others); 

因此,純成員函數仍然可以讀取和修改(對於弱純的)this,因爲它僅僅是參數之一。


就是一個常量和一個不變的成員類之間的區別?

不知道你是什麼意思☺


我應該添加儘可能多的功能屬性越好?

您應該添加最能描述您的功能的功能屬性。如果功能從未被覆蓋,則添加final。如果將從未拋出任何異常,再加入nothrow

(順便說一句,purenothrow@safe可如果函數是一個模板函數推斷。)

3

裁判存儲類在成員函數f的前面是多餘的權利? Class對象始終按引用傳遞,因此返回Bref B是否等同?

添加ref允許您通過寫作來改變b場(實際的參考,而不只是它的內容):a.f() = new B();

二:pure成員函數?

我相信純方法把this當作另一個論點。

第三:const和不可變成員類有什麼區別?區分不可變和const類對象的成員函數調用?在語義上,它是平等的,我們不能改變這兩個屬性的數據成員,對吧?

是的,但immutable版本有更強的保證。

第四:我應該添加儘可能多的功能屬性嗎?像pureconstimmutable,nothrowfinal

添加儘可能多的屬性,因爲使用您正在編寫的代碼時會很有用。 (請注意,目前的實現不太擅長檢測冗餘屬性。)