2010-04-18 57 views
5

東西我看到脂肪酶這樣定義變量:的Objective C/C中的命名約定,以「_」開頭?

b2World *_world; 
b2Body *_body; 
CCSprite *_ball; 

代替

b2World *world; 
b2Body *body; 
CCSprite *ball; 

我熟悉的第二個,但不是第一個。所以,我查了維基百科有關命名約定:

名稱以雙下劃線 或下劃線和一個大寫字母 被保留用於執行 (編譯器,標準庫)和 不應該使用(例如__reserved或 _Reserved)。

那麼,是否有以「_」開頭的特殊含義?

我看到它使用「_」開始的代碼是在這裏:

http://www.raywenderlich.com/457/intro-to-box2d-with-cocos2d-tutorial-bouncing-balls

The wiki page.

回答

0

通常他們用於不應當前文件外部訪問變量/模塊/命名空間/任何,在不支持限制訪問的語言,如private關鍵字

+0

或靜態在C中。 – 2010-04-18 00:37:25

13

在一些Objective-C開發人員之間有一個長期慣例帶有下劃線的efix實例變量。它可以在幾個方面有所幫助:其一,它更容易在.m文件中找到實例變量;第二,它使開發人員不必爲方法參數提供創意名稱,以避免與實例變量名稱相沖突;正如其他人已經指出的那樣,它表明實例變量是私有的,因此在整個代碼中不應該被訪問。

事實上,我會爭取避免直接訪問實例變量,而不是訪問器(獲取者和設置者),-dealloc-init...。並不是說你不應該永遠不要在其他地方使用它們,但是在使用其他方法直接使用實例變量之前,你至少應該考慮一下。

-1

Apple保留以下劃線開頭的名稱作爲其自己的私人ivars和方法。在任何Apple平臺上的Objective-C中,建議您不要用帶下劃線的前綴標識符。

http://developer.apple.com/mac/library/documentation/Cocoa/Conceptual/CodingGuidelines/Articles/NamingMethods.html

+0

-1 Apple *不保留帶有下劃線前綴的實例變量。恰恰相反,他們鼓勵所有開發人員爲ivars使用下劃線前綴;實際上,默認情況下,Xcode 4.5中引入的自動合成機制合成了前綴ivars。 – jlehr 2013-01-09 16:03:20

+0

@jlehr:你的後一點是不正確的。自動合成的ivars默認具有與屬性完全相同的名稱。 – 2013-04-08 08:49:33

+1

@JeremyP:jlehr對他以前的觀點是正確的。你的鏈接指向一篇關於命名方法的文章,而不是ivars。與ivar有關的同伴可以在這裏找到:https://developer.apple.com/library/mac/#documentation/Cocoa/Conceptual/CodingGuidelines/Articles/NamingIvarsAndTypes.html#//apple_ref/doc/uid/20001284-1001757 – 2013-04-08 08:52:16

3

這真的真的很有幫助,但大多數人不知道爲什麼,這是一個恥辱。 Apple使用下劃線來分隔其他對象訪問特定對象變量的方式,以及特定對象訪問其自身變量的方式。 現在,這聽起來有點怪怪的,但想象一下以下內容:你可能都承認以下編譯器警告

.h 
@property (nonatomic, retain, readonly) UITableView *tableView; 

.m 
- (NSInteger)numberOfSectionsInTableView:(UITableView *)tableView { 
    return [self loadSomethingElseForTableView:tableView]; 
} 

這將導致一個編譯器警告,因爲它不知道無論您參考局部變量「tableView」或實例變量。 因此,Apple建議您將以下內容添加到@implementation的頂部。

@synthesize tableView = _tableView; 

現在,當您參考_tableView,編譯器知道你指的是實例變量,而不是本地的。

此外,這使得它更容易理解Obj-C中的垃圾收集,並防止發生常見錯誤。

例如,在做的時候以下幾點:

@property (nonatomic, retain, readonly) NSString *title; 

- (id)initWithTitle:(NSString *)title { 
    if ((self = [super init])) { 
     self.title = title; // Is not possible, since it's read only. 
     title = title; // Is not possible, since it's the same (local) variable. 
     // Changing the method to initWithTitle:(NSString *)aTitle; 
     title = aTitle; 
    } 
    return self; 
} 

現在,既然你不使用默認的setter方法(實際上,你不能,因爲它是隻讀)你需要保留改變你自己。 當你給每個實例變量一個前綴時(這樣你就知道你需要自己保留它),這是很容易記住的。

所以,基本上,瞭解self.variable和(_variable之間的區別很重要。 (即:self.variable映射到[self setVariable:...]variable直接映射到你的指針

此外,當你將它添加爲私有變量,像這樣:

@interface TSSomeObject : NSObject { 
@private 
    NSString *_privateTitle; 
} 
@end 

下劃線前綴是不是真的有必要,除非你可能遇到同名的局部變量,除此之外,它也是一種簡單的方法來提醒你,它是一個本地指針,當你將它指定給對象時,你需要保留(並釋放)變量。

什麼錯誤是創建一個屬性有下劃線前綴,像這樣:

@property (nonatomic, retain) NSString *_title; 

這是真的錯了,我也不打算解釋爲什麼;)


所以,是的!你應該真的使用下劃線前綴,它使你的代碼更容易閱讀,並由編譯器解釋!在Xcode 4中,Apple甚至將這些@synthesize添加到默認模板中。

0

https://developer.apple.com/library/mac/documentation/Cocoa/Conceptual/CodingGuidelines/Articles/NamingIvarsAndTypes.html#//apple_ref/doc/uid/20001284-1001757

兩個由上述文件中公約和建議書,你應該用下劃線前綴的ivars。

不可否認,它的引用是爲屬性顯式設置ivars。

但它的用法是一樣的,以表明在任何地方看到的ivar的用法。

然而,我仍然樂於接受這種可能性,在這種情況下,使用帶下劃線的前綴ivar可能會向用戶發出信號,表示他們做錯了事。同時,一個後綴固定的下劃線可以用於直接訪問的純ivars。

這個博客有一些來自經驗豐富的從業者的好想法,它建議使用前綴下劃線。

http://blog.bignerdranch.com/463-a-motivation-for-ivar-decorations/

無論您選擇使用前綴下劃線來裝飾自己的實例變量,至少有一些證據表明,一些樣的裝修會幫助你避免錯誤。前綴的下劃線是最常見的裝飾。