您好,登錄后才能下訂單哦!
一,
關于OC的實例變量的可見度,即實例變量的訪問權限有三種:
1),@public 公有的
被@public修飾的實例變量是公共的,即沒有訪問權限,在任何文件中都可以訪問,(訪問方式是通過對象+指向操作符)
2),@protected 受保護的
被@protected修飾的實例變量有一定的訪問限,只允許在本類文件及子類文件中訪問,其他文件不可訪問
3),@private 私有的
被@private 修飾的實例變量,只允在在本類文件中訪問,不可以在子類文件以及其他文件中訪問.
這里可以說下私有方法;私有方法即沒有在.h文件中聲明,之間在.m文件中實現的方法,它只允許本類調用,外部無法訪問,即使是子類也無法訪問
二,
我們通常在定義實例變量的時候一般都不再聲明變量的訪問權限,OC默認的是@protected,因為OC面向對象的三大特性:封裝,繼承,多態.如果聲明為public外部就可以訪問以及修改會影響內部的一個實現,暴漏實現細節,不能體現OC面向對象的封裝特性(封裝的思想是隱藏內部的實現).如果聲明為private,子類文件就不可以訪問該實例變量,這樣子類文件需重新定義聲明,這樣違背了OC面向對象的繼承特性,(繼承是指父類的所有實例變量和方法等子類都可以訪問使用.
當定義為protected又需要對該變量重新賦值時,可以利用設置器,即setter方法針對每個實例變量設置一個方法為它賦值,同時利用訪問器,即getter方法針對每個實例變量設置一個方法來獲取它的值
如:舉個人這個類的例子 類名為Person
其實例變量為:
{
NSString *_name; //姓名
NSString *_sex; //性別
NSInteger _age; //年齡
}
1,設置器,getter方法
1)為_name賦值
- (void)setName:(NSString*)name;
2)為_sex賦值
- (void)setSex:(NSString*)sex;
3)為_age賦值
-(void)setAge:(NSInteger)age;
2,訪問器 getter方法
1)讀取_name的值
- (NSString *)name;
2)讀取_sex的值
- (NSString *)sex;
3)讀取_age的值
- (NSInteger)age;
三,
類的繼承
1,當多個類出現部分相同的實例變量和方法時就要考慮用繼承, 繼承時將多個類中相同的實例變量的方法提出來寫成一個公共的父類.
子類繼承父類: 會將父類中除了聲明為@private的實例變量以及私有方法外,其余內容都會被繼承們所有如果子類中有和父類同樣的內容,可以全部刪除.
私有方法 :即沒在.h文件中聲明,只在,m文件中實現了該方法,對于私有方法不允許外部訪問,只能讓本類調用訪問
一個類繼承另一個類時要在.h文件的@interface開頭地方把它的父類寫在:號后面如,一個學生類Student繼承了Person類
@interface Student:Person
2,繼承時方法存在三種:
1),保留父類對該方法的實現,(實現方法不重寫)
2),按子類重寫后的方式來實現(實現方式重寫方法,寫自己的實現體完全忽略父類的實現)
3),對于該方法既有父類的方法實現也有子類對該方法的實現,在這種情況下我們一般在方法的實現內容里先把調用父類方法的實現即用[super (方法)]這個方法名是就是繼承過來的方法名,然后再實現子類特有的行為
3,這里需要重點說一下繼承類時自定義初始化的實現方法
首先自定義初始化的方法名必須是init+Whith開頭,返回值是(id),是”-”號方法,
當子類有獨有的實例變量時如:
{
NSString *_num;
NSString *_course;
}
多了一個學號和課程,初始化時子類只對自己獨有的實例變量賦值即可,super調用父類對初始化方法的實現,為從父類繼承過來的實例變量賦值,這里的self還是調用方法時的值返回給自己,誰調用就返回給誰,如果賦值不成功即self == nil,這時子類不在賦值,因為如果父類的實例變量賦值失敗了,子類的賦值也就毫無意義了
-(id)initWithname:(NSString*)name sex:(NSString *)sex age:(NSInteger)age num:(NSString *)numcourse:(NSString *)course
{
self = [super initWithname:name sex:sexage:age];
if(self != nil) {
_course= course;
_num= num;
}
return self;
}
四,便利構造器
我們在main函數里創建對象接收消息時往往在創建對象時需要給對象開辟空間和初始化,這樣可能比較麻煩, 我們在定義類的時候直接實現為對象開辟空間,即便利構造器
作用:快速創建對象,內部封裝了創建對象的過程,
格式: 1. +號方法,
2, 返回值為id類型,
3, 以類名+With開頭,拼接上多個參數
還以上述學生類Student類繼承人類Person為例
1)在.h文件里寫方法的聲明,
在這里該方法為”+”號方法
+ (id)studentWithname:(NSString *)name sex:(NSString*)sex age:(NSInteger)age num:(NSString *)num course:(NSString *)course;
2)在.m文件里寫方法的實現
+ (id)studentWithname:(NSString *)name sex:(NSString*)sex age:(NSInteger)age num:(NSString *)num course:(NSString *)course
{
return [[Studentalloc] initWithname:name sex:sex age:age num:num course:course];
}
五,
類的循環調用的有關問題
該問題一般用于解決一個類實例變量里需要用到另一個類的所有變量
例如一個家庭類,成員有爸爸,媽媽,兒子,這三個類建立每個都需要另一個類的內容如爸爸類實例變量有姓名年齡,妻子,兒子. 這里妻子和兒子的類型就是妻子類和兒子類的類名 + * ,這時要循環調用,在遇到循環調用時需要導入文件,但是這里的導入文件不能直接在該類的.h文件用”#import “頭文件”” 導入文件,因為這個類還沒有定義,無法識別,再使用該類時不能把它當做一個類而所以在該類的.h文件里使用”@ class + 要調用的類名”,將要調用的類聲明為一個字符串,但是它不具備的類的內容 ,所以要在該類的.m文件里用”#import“頭文件””導入頭文件.下面舉個家庭的例子
1)男人類
(.h文件里)
@class Woman;
#import "Child.h"
@interface Man : NSObject
{
NSString*_name; //姓名
NSString*_sex; //性別
NSInteger_age; //年齡
Woman*_wife; //妻子
}
//設置妻子
- (void)setWife:(Woman *)wife;
//設置孩子
- (void)setChild:(Child *)baby;
//訪問姓名
- (NSString *)name;
//為_sex賦值
- (void)setSex:(NSString *)sex;
//為_age賦值
- (void)setAge:(NSInteger)age;
- (id)initWithName:(NSString *)name Sex:(NSString*)sex Age:(NSInteger)age;
//輸出一個人的信息
- (void)print;
@end
(.m文件里)
#import "Man.h"
#import "Woman.h"
@implementation Man
- (void)setWife:(Woman *)wife
{
_wife =wife;
}
- (void)setChild:(Child *)baby
{
_baby =baby;
}
//訪問姓名
- (NSString *)name
{
return_name;
}
//為sex賦值
- (void)setSex:(NSString *)sex
{
_sex =sex;
}
//為age賦值
- (void)setAge:(NSInteger)age
{
_age =age;
}
- (id)initWithName:(NSString *)name Sex:(NSString*)sex Age:(NSInteger)age
{
_name =name;
_sex =sex;
_age =age;
returnself; }
-(void)print
{
NSLog(@"I am a man,My name is %@,My wife's name is %@, My baby'sname is %@",_name,[_wife name],[_baby name]);
}
其中女人類和孩子類跟男人類相似,只是調用的類有所不同,這里不再贅述
免責聲明:本站發布的內容(圖片、視頻和文字)以原創、轉載和分享為主,文章觀點不代表本網站立場,如果涉及侵權請聯系站長郵箱:is@yisu.com進行舉報,并提供相關證據,一經查實,將立刻刪除涉嫌侵權內容。