協議 protocal
暫時忽略這個,因為我覺得在C++中,多重繼承都不是太常用P124
異常處理
在可能會拋出異常的代碼塊用@try標記
@catch指令標記的代碼塊,用於捕捉@try語句塊中的拋出的錯誤
@finally語句塊中包含的代碼是不論程序是否拋出異常都會執行的代碼
可以使用@throw自己拋出一個錯誤,這個錯誤一般熟NSException類的對象
試個例子P130
[cpp]
//
// main.m
// test
//
// Created by Zeng on 13-5-24.
// Copyright (c) 2013年 zeng. All rights reserved.
//
#import <Foundation/Foundation.h>
#import "YourClub.h"
#import "Membership.h"
#import "MyClass.h"
int main(int argc, const char * argv[])
{
NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init];
MyClass *class1 = [[MyClass alloc] init];
@try {
[class1 release];
}
@catch (NSException *exception) {
NSLog(@"Caught %@ %i", [class1 name], [class1 age]);
}
@finally {
NSLog(@"OK");
}
[pool release];
return 0;
}
//
// main.m
// test
//
// Created by Zeng on 13-5-24.
// Copyright (c) 2013年 zeng. All rights reserved.
//
#import <Foundation/Foundation.h>
#import "YourClub.h"
#import "Membership.h"
#import "MyClass.h"
int main(int argc, const char * argv[])
{
NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init];
MyClass *class1 = [[MyClass alloc] init];
@try {
[class1 release];
}
@catch (NSException *exception) {
NSLog(@"Caught %@ %i", [class1 name], [class1 age]);
}
@finally {
NSLog(@"OK");
}
[pool release];
return 0;
}
回憶一個指針的類型和指針所指向的類型
int *prt;//指針的類型是int*
int **prt;//指針的類型是int**
int (*ptr)[3]//指針的類型是int(*)[3]
int *(* ptr)[4]//指針的類型是int*(*)[4]
從語法上看,只須把指針聲明語句中的指針名字和名字左邊的指針聲明符*去掉,剩下的就是指針所指向的類型,例如上面的:
int *prt;//指針的類型是int
int **prt;//指針的類型是int*
int (*ptr)[3]//指針的類型是int()[3]
int *(* ptr)[4]//指針的類型是int*()[4]
從上面可以看出,指針的類型(即指針本身的類型)和指針所指向的類型是兩個概念
線程暫時沒用到,先不做學習,等用到的時候在回來看P134
單例模式,P135,挺好的一種設計模式,能在例子中學習到靜態方法+
[cpp]
//
// main.m
// test
//
// Created by Zeng on 13-5-24.
// Copyright (c) 2013年 zeng. All rights reserved.
//
#import <Foundation/Foundation.h>
@interface Singleton : NSObject{
NSString *name;
int age;
}
@property(nonatomic, copy) NSString *name;
@property int age;
@end
@implementation Singleton
@synthesize name, age;
static Singleton *singleton = nil;
// 單例的主要方法
+(Singleton *)getSingleton{
if (singleton == nil) {
singleton = [[super allocWithZone:NULL]init];
}
return singleton;
}
+(id)allocWithZone:(NSZone *)zone{
return [[self getSingleton] retain]; // 返回單例
}
-(id)copyWithZone:(NSZone *)zone{
return self;
}
-(id)retain{
return self;
}
-(NSUInteger)retainCount{
return NSUIntegerMax;
}
-(void)release{
}
-(id)autorelease{
return self;
}
@end
int main(int argc, const char * argv[])
{
NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init];
Singleton *singleton = [Singleton getSingleton];
[singleton setName:@"zengraoli"];
[singleton setAge:36];
NSLog(@"name : %@, age is : %i", [singleton name], [singleton age]);
Singleton *singleton2 = [Singleton getSingleton];
NSLog(@"name : %@, age is : %i", [singleton2 name], [singleton2 age]);
[pool release];
return 0;
}
//
// main.m
// test
//
// Created by Zeng on 13-5-24.
// Copyright (c) 2013年 zeng. All rights reserved.
//
#import <Foundation/Foundation.h>
@interface Singleton : NSObject{
NSString *name;
int age;
}
@property(nonatomic, copy) NSString *name;
@property int age;
@end
@implementation Singleton
@synthesize name, age;
static Singleton *singleton = nil;
// 單例的主要方法
+(Singleton *)getSingleton{
if (singleton == nil) {
singleton = [[super allocWithZone:NULL]init];
}
return singleton;
}
+(id)allocWithZone:(NSZone *)zone{
return [[self getSingleton] retain]; // 返回單例
}
-(id)copyWithZone:(NSZone *)zone{
return self;
}
-(id)retain{
return self;
}
-(NSUInteger)retainCount{
return NSUIntegerMax;
}
-(void)release{
}
-(id)autorelease{
return self;
}
@end
int main(int argc, const char * argv[])
{
NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init];
Singleton *singleton = [Singleton getSingleton];
[singleton setName:@"zengraoli"];
[singleton setAge:36];
NSLog(@"name : %@, age is : %i", [singleton name], [singleton age]);
Singleton *singleton2 = [Singleton getSingleton];
NSLog(@"name : %@, age is : %i", [singleton2 name], [singleton2 age]);
[pool release];
return 0;
}
繼承:
這裡只需要注意方法重寫和重載就行,不過這又和C++的差不多了
重寫:
返回值、方法名、類型、參數類型、參數個數都相同
重載:
1、方法名相同
2、方法名的參數表必須不同,包括參數的類型和個數,以此區分不同的方法體
3、方法的返回類型、修飾符可以相同,也可以不同
OC沒有像java那樣,所謂的abstract類
id類型的使用,主要是可以取代*,和指針的使用差不多
[cpp]
//
// main.m
// test
//
// Created by Zeng on 13-5-24.
// Copyright (c) 2013年 zeng. All rights reserved.
//
#import <Foundation/Foundation.h>
#import "YourClub.h"
#import "Membership.h"
#import "MyClass.h"
int main(int argc, const char * argv[])
{
NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init];
id idMyClass;
MyClass *class1 = [[MyClass alloc] init];
[class1 setName:@"zengraoli1" andSetTheAge:36];
MyClass *class2 = [[MyClass alloc] init];
[class2 setName:@"zengraoli2" andSetTheAge:63];
idMyClass = class1;
NSLog(@"name : %@, age : %i", [idMyClass name], [idMyClass age]);
idMyClass = class2;
NSLog(@"name : %@, age : %i", [idMyClass name], [idMyClass age]);
[class1 release];
[class2 release];
[pool release];
return 0;
}
//
// main.m
// test
//
// Created by Zeng on 13-5-24.
// Copyright (c) 2013年 zeng. All rights reserved.
//
#import <Foundation/Foundation.h>
#import "YourClub.h"
#import "Membership.h"
#import "MyClass.h"
int main(int argc, const char * argv[])
{
NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init];
id idMyClass;
MyClass *class1 = [[MyClass alloc] init];
[class1 setName:@"zengraoli1" andSetTheAge:36];
MyClass *class2 = [[MyClass alloc] init];
[class2 setName:@"zengraoli2" andSetTheAge:63];
idMyClass = class1;
NSLog(@"name : %@, age : %i", [idMyClass name], [idMyClass age]);
idMyClass = class2;
NSLog(@"name : %@, age : %i", [idMyClass name], [idMyClass age]);
[class1 release];
[class2 release];
[pool release];
return 0;
}
category(類別)
category是OC裡面最常用到的功能之一。category可以為已經存在的類增加方法,而不需要增加一個子類。另外,category使得我們在不知道某個類的內部實現的情況下,為該類增加方法。
如果我們想增加某個框架(framewordk)中的類的方法,category就非常有效。比如,如果想在NSString上增加一個方法來判斷它是否是一個URL,那可以這麼做:
[cpp]
#import
@interface NSString (Utilities)
- (BOOL) isURL
@end
#import
@interface NSString (Utilities)
- (BOOL) isURL
@end
P156、P157試一個使用category的例子
注意,類別並不能為類聲明新的實例變量,它只包含方法。
NSStringUtiities.h
[cpp]
//
// NSStringUtiities.h
// test
//
// Created by Dawn on 13-5-27.
// Copyright (c) 2013年 zeng. All rights reserved.
//
#import <Foundation/Foundation.h>
#import "Cocoa/cocoa.h"
@interface NSString (Utilities)
-(BOOL) isURL;
@end
//
// NSStringUtiities.h
// test
//
// Created by Dawn on 13-5-27.
// Copyright (c) 2013年 zeng. All rights reserved.
//
#import <Foundation/Foundation.h>
#import "Cocoa/cocoa.h"
@interface NSString (Utilities)
-(BOOL) isURL;
@end
NSStringUtiities.m:
[cpp]
//
// NSStringUtiities.m
// test
//
// Created by Dawn on 13-5-27.
// Copyright (c) 2013年 zeng. All rights reserved.
//
#import "NSStringUtiities.h"
@implementation NSString (Utilities)
-(BOOL) isURL{
if ([self hasPrefix:@"http://"]) {
return YES;
}else{
return NO;
}
}
@end
//
// NSStringUtiities.m
// test
//
// Created by Dawn on 13-5-27.
// Copyright (c) 2013年 zeng. All rights reserved.
//
#import "NSStringUtiities.h"
@implementation NSString (Utilities)
-(BOOL) isURL{
if ([self hasPrefix:@"http://"]) {
return YES;
}else{
return NO;
}
}
@end
main.m:
[cpp]
//
// main.m
// test
//
// Created by Zeng on 13-5-24.
// Copyright (c) 2013年 zeng. All rights reserved.
//
#import <Foundation/Foundation.h>
#import "NSStringUtiities.h"
int main(int argc, const char * argv[])
{
NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init];
NSString *string1 = @" http://www.baidu.com";
NSString *string2 = @"Ozr";
if ([string1 isURL]) {
NSLog(@"string is URL");
}else{
NSLog(@"string is not URL");
}
if ([string2 isURL]) {
NSLog(@"string isURL");
}else{
NSLog(@"string is not URL");
}
[pool release];
return 0;
}
//
// main.m
// test
//
// Created by Zeng on 13-5-24.
// Copyright (c) 2013年 zeng. All rights reserved.
//
#import <Foundation/Foundation.h>
#import "NSStringUtiities.h"
int main(int argc, const char * argv[])
{
NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init];
NSString *string1 = @" http://www.baidu.com";
NSString *string2 = @"Ozr";
if ([string1 isURL]) {
NSLog(@"string is URL");
}else{
NSLog(@"string is not URL");
}
if ([string2 isURL]) {
NSLog(@"string isURL");
}else{
NSLog(@"string is not URL");
}
[pool release];
return 0;
}
上邊的代碼其實是對NSString做了一個小的擴展
OC中的宏定義和條件編譯#ifndef跟C++中是一樣的,需要注意這個:
如果在宏定義的參數之前防止一個#,那麼在調用該宏的時候,預處理程序根據宏參數創建C語言風格的常量字符串。
例如:
#define str(x) #x
在後面的調用為str(test);得到的結果為"test"
Foundation Framework
可以查看方法的DOC-----------P170
數字對象NSNumber
[java]
//
// main.m
// test
//
// Created by Zeng on 13-5-24.
// Copyright (c) 2013年 zeng. All rights reserved.
//
#import <Foundation/Foundation.h>
#import "YourClub.h"
#import "Membership.h"
#import "MyClass.h"
#import "NSStringUtiities.h"
int main(int argc, const char * argv[])
{
NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init];
NSNumber *myNumber, *floatNumber, *intNumber;
// 創建integer類型對象
intNumber = [NSNumber numberWithInteger:123];
NSLog(@"%li", [intNumber integerValue]);
// 創建long類型對象
myNumber = [NSNumber numberWithLong:0xababab];
NSLog(@"%lx", [myNumber longValue]);
// 創建char類型對象
myNumber = [NSNumber numberWithChar:'K'];
NSLog(@"%c", [myNumber charValue]);
// 創建float類型對象
floatNumber = [NSNumber numberWithFloat:123.9];
NSLog(@"%f", [myNumber floatValue]);
// 創建double類型對象
myNumber = [NSNumber numberWithDouble:12233e+15];
NSLog(@"%lg", [myNumber doubleValue]);
// 判斷兩個對象是否相等
if ([intNumber isEqualToNumber:floatNumber] == YES) {
NSLog(@"值相等");
}else{
NSLog(@"值不等");
}
// 比較兩個對象的值大小
if ([intNumber compare:myNumber] == NSOrderedAscending) {
NSLog(@"左邊的數字小");
}else{
NSLog(@"左邊的數字大");
}
[pool release];
return 0;
}
//
// main.m
// test
//
// Created by Zeng on 13-5-24.
// Copyright (c) 2013年 zeng. All rights reserved.
//
#import <Foundation/Foundation.h>
#import "YourClub.h"
#import "Membership.h"
#import "MyClass.h"
#import "NSStringUtiities.h"
int main(int argc, const char * argv[])
{
NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init];
NSNumber *myNumber, *floatNumber, *intNumber;
// 創建integer類型對象
intNumber = [NSNumber numberWithInteger:123];
NSLog(@"%li", [intNumber integerValue]);
// 創建long類型對象
myNumber = [NSNumber numberWithLong:0xababab];
NSLog(@"%lx", [myNumber longValue]);
// 創建char類型對象
myNumber = [NSNumber numberWithChar:'K'];
NSLog(@"%c", [myNumber charValue]);
// 創建float類型對象
floatNumber = [NSNumber numberWithFloat:123.9];
NSLog(@"%f", [myNumber floatValue]);
// 創建double類型對象
myNumber = [NSNumber numberWithDouble:12233e+15];
NSLog(@"%lg", [myNumber doubleValue]);
// 判斷兩個對象是否相等
if ([intNumber isEqualToNumber:floatNumber] == YES) {
NSLog(@"值相等");
}else{
NSLog(@"值不等");
}
// 比較兩個對象的值大小
if ([intNumber compare:myNumber] == NSOrderedAscending) {
NSLog(@"左邊的數字小");
}else{
NSLog(@"左邊的數字大");
}
[pool release];
return 0;
}
來看看這行代碼:
NSAutoreleasePool *pool =[[NOSAutoreleasePool alloc] init];
這行代碼為我們分配了pool的自動釋放池預留了內存空間。自動釋放池可以自動釋放添加到該池中的對象所使用的內存。當給對象發送一條autorelease消息時,就將該對象放到這個池中。釋放這個池時,添加到該池中的所以對象都會一起被釋放,因此所以這樣的對象都會被銷毀,除非已經指明了這些對象所在的作用域超出自動釋放池。
NSInteger其實是typedef long
裡面的方法可以通過查看DOC來使用