OC學習篇之---@class關鍵字的做用以及#include和#import的區別 分類: IOS 2014-12-06 13:09 3920人閱讀 評論(0) 收藏

前一篇文章說到了OC中類的三大特性:http://blog.csdn.net/jiangwei0910410003/article/details/41707161今天咱們來看一下在學習OC的過程當中遇到的一些問題,該如何去解決,首先來看一下咱們以前遺留的一個問題:學習


1、#import和#include的區別測試

當咱們在代碼中使用兩次#include的時候會報錯:由於#include至關於拷貝頭文件中的聲明內容,因此會報重複定義的錯誤spa

可是使用兩次#import的話,不會報錯,因此他能夠解決重複導入的問題,他會作一次判斷,若是已經導入一次就不導入了.net


2、關鍵字@class的做用指針

在來看一下OC中的關鍵字@class的做用,在看他的做用以前,先來看一個問題:code

如今有一個課程類Classes和學生類Student,他們兩之間須要相互引用(導入)。直接看代碼比較直接:blog

Classes.hip

//
//  Classes.h
//  08_@class
//
//  Created by jiangwei on 14-10-11.
//  Copyright (c) 2014年 jiangwei. All rights reserved.
//

#import <Foundation/Foundation.h>

#import "Student.h"

//不會將Student.h拷貝過來,只是告訴編譯器Student這個類在別的地方中有定義,這樣就不知道這個類中任何信息(哪些屬性和方法)
//@class Student;

@interface Classes : NSObject{
    
@public
    Student *_student;
}

- (void)t1;

@end

導入Student.h頭文件


Classes.mget

//
//  Classes.m
//  08_@class
//
//  Created by jiangwei on 14-10-11.
//  Copyright (c) 2014年 jiangwei. All rights reserved.
//

#import "Classes.h"

//#import "Student.h"

@implementation Classes

- (void)t1{
    [_student work];
}

@end


在來看一下Student類

Student.h編譯器

//  Student.h
//  08_@class
//
//  Created by jiangwei on 14-10-11.
//  Copyright (c) 2014年 jiangwei. All rights reserved.
//

#import <Foundation/Foundation.h>

#import "Classes.h"

@interface Student : NSObject{
    Classes *_classes;
}

- (void)work;

@end
一樣的也導入Classes.h頭文件


Student.m

//
//  Student.m
//  08_@class
//
//  Created by jiangwei on 14-10-11.
//  Copyright (c) 2014年 jiangwei. All rights reserved.
//

#import "Student.h"

@implementation Student

- (void)work{
    NSLog(@"work");
}

@end


在來看一下測試代碼:

main.m

//
//  main.m
//  08_@class
//
//  Created by jiangwei on 14-10-11.
//  Copyright (c) 2014年 jiangwei. All rights reserved.
//

#import <Foundation/Foundation.h>

#import "Classes.h"
#import "Student.h"

//Classes和Student相互導入會出現問題
//這時候咱們就能夠使用@class解決這樣的問題
//咱們通常在.h文件中使用@class,由於在.h文件中通常是不會使用類的屬性和方法的
//在.m文件中能夠導入.h文件
int main(int argc, const char * argv[]) {
    @autoreleasepool {
        Classes *cls =[[Classes alloc] init];
        Student *stu = [[Student alloc] init];
        cls->_student = stu;
        [cls t1];
        
    }
    return 0;
}
這裏有一個問題注意一下:咱們看到了這裏是如何使用Classes中的屬性_student的,由於在Classes類中屬性_student是@public的,因此能夠直接使用,用的是箭頭符號,和C/C++中的指針變量調用差很少。記住了,這裏就說到了如何直接訪問一個類中的@public修飾符的屬性變量


咱們編譯運行:

看到了,編譯錯誤,說在Student類中的Classes類找不到指定類型,這就奇怪了,咱們不是導入了Classes.h文件了,爲何仍是找不到類型呢?

這就是OC中類的相互引用的問題,咱們在Student.h文件中導入了Classes.h,又在Classes.h文件中導入了Student.h,OC中在相互導入的時候編譯是不經過的

這樣就會致使錯誤。

固然解決辦法就是使用@class關鍵字,咱們修改一下Classes類

Classes.h

//
//  Classes.h
//  08_@class
//
//  Created by jiangwei on 14-10-11.
//  Copyright (c) 2014年 jiangwei. All rights reserved.
//

#import <Foundation/Foundation.h>

//#import "Student.h"

//不會將Student.h拷貝過來,只是告訴編譯器Student這個類在別的地方中有定義,這樣就不知道這個類中任何信息(哪些屬性和方法)
@class Student;

@interface Classes : NSObject{
    
@public
    Student *_student;
}

- (void)t1;

@end
咱們將#import "Student.h"代碼註釋了,使用

@class Student

這段代碼的做用就是不會將Student.h文件拷貝過來,只是告訴編譯器Student這個類在別的地方中有定義,這樣就不知道這個類中的任何信息了(哪些屬性和方法)

Classes.m

//
//  Classes.m
//  08_@class
//
//  Created by jiangwei on 14-10-11.
//  Copyright (c) 2014年 jiangwei. All rights reserved.
//

#import "Classes.h"

#import "Student.h"

@implementation Classes

- (void)t1{
    [_student work];
}

@end
而後在Classes.m文件中導入#import "Student.h"文件,這時候編譯就不會報錯了,一樣就能夠正常的運行了:



總結

這一篇文章就介紹了#import關鍵字和@class的做用,特別是@class關鍵字的使用,爲了解決相互導入的問題,在此回顧一下咱們是怎麼操做的:

Student類中的導入Classes.h方式不變,在Classes.h頭文件中使用@class關鍵字引入Student類型,使其編譯經過,而後在Classes.m文件中導入Student.h文件,使其運行經過。

之後遇到這樣的問題解決方法就是這樣操做的。

相關文章
相關標籤/搜索