---------------------------------------- android培訓、java培訓、期待與您交流! ------------------------------------
一、內存管理相關概念(瞭解)
1、殭屍對象:所佔用內存已經被回收的對象,殭屍對象不能再使用
2、野指針:指向殭屍對象(不可用內存)的指針,給野指針發送消息會報錯(EXC_BAD_ACCESS: 訪問了一塊壞的內存(已經被回收、已經不可用的內存)
3、空指針:沒有指向任何東西的指針(存儲的東西是nil、NULL、0),給空指針發送消息不會報錯(OC不存在空指針錯誤)
二、內存管理方法的使用(熟練掌握)
1、retain :計數器+1,會返回對象本身
2、release :計數器-1,沒有返回值
3、retainCount :獲取當前的計數器
4、 dealloc
1) 當一個對象要被回收的時候,就會調用
2)一定要調用[super dealloc],這句調用要放在最後面
三、內存管理原則(謹記!!!)
1、誰創建,誰release
1)如果你通過alloc、new或[mutable]copy來創建一個對象,那麼你必須調用release或autorelease
2) 換句話說,不是你創建的,就不用你去[auto]release
2、誰retain,誰release
1)只要你調用了retain,無論這個對象是如何生成的,你都要調用release
2)曾經讓對象的計數器+1,就必須在最後讓對象計數器-1
四、代碼演示
1、創建兩個對象Book和Person
1)Person聲明 Person.h(Ps:人能擁有書,所以使用組合方式)
#import <Foundation/Foundation.h>
#import "Book.h"//導入所要組合的Book類
@interface Person : NSObject
{
Book * _book ; //定義book成員變量:由於演示內存管理,就先不用property,用手動get和set!
}
- (void)setBook:(Book *)book;
- (Book *)book;
@end
Person實現Person.m(嚴謹遵循內存管理思想!!!)
#import "Person.h"//導入Person頭文件,在person.h文件中組合了Book類
@implementation Person
- (void)setBook:(Book *)book{
if (book != _book ) //當傳入對象爲同一對象
{
// 對當前正在使用的書(舊書)做一次release
[_book release];
// 對新書做一次retain操作,使book計數器+1
_book = [book retain];
}
}
-(Book *)book{
return _book;
}
//當person計數器爲0時,調用dealloc方法,打印:Person對象被回收!
-(void)dealloc{
[_book release]; //當人死掉的時候,也要把書的計數器釋放掉-1
NSLog(@"Person對象被回收!");
[super dealloc];
}
@end
2)Book.m
#import "Book.h" //導入Book的聲明,定義了成員變量price,此處省略Book.h代碼
@implementation Book
- (void) setPrice:(int)price{
_price = price;
}
- (int) price{
return _price;
}
//當book計數器爲0時,調用dealloc方法,打印:Book對象被回收!
-(void)dealloc{
NSLog(@"Book對象被回收!");
[super dealloc];
}
@end
3) main.m
#import <Foundation/Foundation.h>
#import "Person.h" //由於Person組合了Book,所以只要導入Person.h即可
int main()
{
//1、創建Book對象,當前Book計數器爲1,b在使用book
Book *b = [[Book alloc] init];
//創建Person對象,Person計數器爲1
Person *p = [[Person alloc] init];
//2、p來使用b這本書,內部實現book計數器+1,當前book=2
[p setBook:b];
//3、變量b不想用這本書了,讓book計數器-1 當前book=1;
[b release];
//清空對象
b = nil;
//4、當人p掛掉,也要負責把book計數器-1 當前book = 0
[p release];
p = nil;
return 0;
}
4)程序輸出:
2014-03-23 11:57:02.338 內存管理[372:303] Book對象被回收!
2014-03-23 11:57:02.349 內存管理[372:303] Person對象被回收!
五、內存管理代碼規範:
1.只要調用了alloc,必須有release(autorelease)
對象不是通過alloc產生的,就不需要release
2.set方法的代碼規範
1> 基本數據類型:直接複製
- (void)setAge:(int)age
{
_age = age;
}
2> OC對象類型
- (void)setCar:(Car *)car
{
// 1.先判斷是不是新傳進來對象
if ( car != _car )
{
// 2.對舊對象做一次release
[_car release];
// 3.對新對象做一次retain
_car = [car retain];
}
}
3.dealloc方法的代碼規範
1> 一定要[super dealloc],而且放到最後面
2> 對self(當前)所擁有的其他對象做一次release
- (void)dealloc
{
[_car release];
[super dealloc];
}
------------------------------------- android培訓、java培訓、期待與您交流! ---------------------------------------