2012-08-17 53 views
7
@interface Foo : NSObject 

{ 
    extern int gGlobalVar; 
    int i; 
} 
-(void)setgGlobalVar:(int)val; 

@end 


@implementation Foo 

-(void)setgGlobalVar:(int)val 
{ 
    i = 5; 
    NSLog(@"i = %i", i); 
    gGlobalVar = val; 
} 

@end 

我可以在接口中聲明i並在實現中使用它,不會有任何錯誤。但我不能在界面中聲明extern類型的變量。這是爲什麼?爲什麼我得到一個錯誤說:「類型名稱不允許指定存儲類」?類型名稱不允許指定存儲類

回答

13

簡述: 的括號中的部分一類的@interface@implementation僅供聲明實例變量(又名「伊娃」)。 extern關鍵字僅用於全局變量聲明(或函數,但這是另一個主題)。
因此,您無法聲明extern ivar。

堅硬的細節: 變量先聲明,然後定義。對於局部範圍內的變量,這種區別通常是模糊的,因爲沒有明確定義的本地聲明變量通常會被編譯器分配並賦予默認值。

全局變量可能在任何範圍內可用,前提是範圍知道全局存在。這就是關鍵字extern進來的地方 - 它宣佈該全局變量存在,並且定義其他地方。只有當你想在不同的代碼文件中訪問一個全局變量時,這纔有用。

最佳實踐:你的書有一些代碼,聲明在實現文件的extern變量(例如「.M」文件,等等。)......,可以工作,但它是一個不好的做法,因爲你對於這個全球在其他地方是否有一個有效的定義做出了潛在的錯誤假設。 (但是,花哨的編譯器會發現這種類型的錯誤。)

相反,最好的做法是在頭文件中聲明一個extern變量,並附帶一個專用於定義該頭中extern的實現文件,以及然後在希望使用該全局變量的其他實現文件中包含該頭文件。

+0

感謝您的回覆HachiEthan。巧合的是,我所指的這本書在'.m'文件中使用了'extern'。 – 2012-08-17 17:00:29

+0

@Rut做一點研究,因爲我還沒有深入到extern的本質之前! (它會幫助我完成當前的工作。)很快會更新答案。 =) – MechEthan 2012-08-17 17:07:57

+0

真的很感激它HachiEthan! – 2012-08-17 17:10:26

相關問題