OC类、消息
1、类的声明
#import ...
@interface className : parentClass <...>
{
//实例变量
}
//方法声明
@end
1.1 #import:本身就有防止头文件被重复包含的功能
1.2 NSObject:OC定义的一个根类,每一个新建的OC类都应该为其派生类,提供了大量的方法(如init、alloc等)
1.3 方法声明一般格式:mType (returnType) name : (type) param name : (type) param==方法类型(返回值类型)标签名:(参数类型)参数名 标签名:(参数类型)参数名
1.4 所有的标签名和冒号构成了整个方法的方法名,如上例方法名:name:name:....
1.5 方法类型:+类方法,相当于c++中的静态成员函数; -实例方法
1.6 OC不支持静态成员变量,可以通过静态全局变量来实现静态成员变量的功能
2、类的实现
#import ...
@implementation className
//方法实现
@end
2.1 方法实现一般格式:mType (returnType) name : (type) param name : (type) param { 。。。}
2.2 方法原型必须和它的声明保持一致
2.3 实例方法可以通过名字引用本类或本类中继承过来的实例变量,但是在类方法中不可以引用实例变量
2.4 在一个方法中,可以用标示符self表示调用方法的对象,类似this
2.5 if(self = [super init]):初始化子类中来自于父类的实例变量,赋给self,if判断是否初始化成功并赋值成功,如果成功则继续初始化子类的实例变量
3、消息机制
3.1 [object foo:10] 称为消息发送,给对象object发送foo:消息
3.2 一般格式为[receiver message]; message与方法在执行阶段绑定,与消息绑定的方法可以是实例方法,也可以是类方法;如果receiver是类,则关联的是类方法,如果receiver是实例,则关联的是实例方法
A、简单OC类
Person.h
#import <Foundation/Foundation.h> //import本身就有防止头文件被重复包含的功能,实现了C++中的#ifndef XXX #define XXX #include <..> ... #endif
@interface Person : NSObject //class Person : ... NSObject,OC定义的根类,每一个新建的OC类都应该为其派生类,提供了大量方法(init、alloc等)
{
float height; //默认protected
double weight; //实例变量与方法的声明分开
}
//Person (float h, double w);
//void print();
//float getHeight();
//double getWeight();
//void setHeightandWeight(float h, double w);
@property (nonatomic, assign)float height; //同类型可以写一起
@property double weight; //声明属性,让编译器自动合成setter和getter方法
- (Person *) initWithHeight : (float) h andWeight : (double) w; //方法的声明,-表示实例方法,+表示类方法(相当于C++的静态成员函数)
- (void) print;
//- (float) height;
//- (double) weight; //声明get方法
- (void) setHeight: (float)h andWeight: (double)w;
+ (void) printWord;
@end //结束,相当于C++类中的;
Person.m
#import "Person.h"
@implementation Person
@synthesize height;
@synthesize weight; //实现,setter和getter方法
- (Person *) initWithHeight : (float) h andWeight : (double) w //不需要 类名::,方法原型与声明一致
{
if (self = [super init]) //self类似于this指针,[super init]初始化子类中来自于父类的实例变量,赋给self,通过if判断是否初始化并赋值成功
{
height = h; //继续初始化子类的实例变量
weight = w;
//self.weight = w; //调用set方法,前提是声明了set方法
}
return self;
}
- (void) print
{
NSLog(@"height = %f, weight = %lf",height, weight);
}
//- (float) height
//{
// return height;
//}
//- (double) weight
//{
// return weight;
//}
- (void) setHeight: (float)h andWeight: (double) w
{
height = h;
weight = w;
}
+ (void) printWord
{
NSLog(@"WWWWWWWWWWW");
}
@end
main.m
#import <Foundation/Foundation.h>
#import "Person.h"
int main(int argc, const char * argv[])
{
@autoreleasepool //自动释放池
{
[Person printWord]; //[接收者 消息]; 类对应类方法,实例对应实例方法
Person *p = [[Person alloc] initWithHeight:1 andWeight:2];
//Person *p = [[Person alloc] init];
[p print];
[p setHeight:3 andWeight:4]; //[接收者 方法名:参数];
NSLog(@"height:%f,weight:%lf",p.height, p.weight);
[p setHeight:5]; //与上面set..and是不同的方法,property和synthesize声明实现了这种方法
[p setWeight:6];
[p print];
p.height = 7; //赋值调set,用值调get
p.weight = 8;
NSLog(@"height:%f,weight:%lf",p.height, p.weight);
//[p release]; //自动释放池不需要再手动释放
}
return 0;
}
B、从C语言说起~
#import <Foundation/Foundation.h>
typedef enum{ kCircle, kRectangle, kOblateSpheroid } ShapeType;
typedef enum{ kRedColor, kGreenColor, kBlueColor } ShapeColor;
typedef struct {
int x, y, width, height;
}ShapeRect;
typedef struct {
ShapeType type;
ShapeColor fillColor;
ShapeRect bounds;
}Shape;
NSString *colorName (ShapeColor colorName)
{
switch (colorName)
{
case kRedColor:
return @"red";
break;
case kGreenColor:
return @"green";
break;
case kBlueColor:
return @"blue";
break;
default:
return @"No";
break;
}
}
void drawCircle (ShapeRect bounds, ShapeColor fillColor)
{
NSLog(@"Circle (%d %d %d %d) in %@", bounds.x, bounds.y, bounds.width, bounds.height, colorName(fillColor));
}//仅实现了画圆
void drawShapes (Shape shapes[], int count)
{
int i;
for (i = 0; i < count; i++)
{
switch (shapes[i].type)
{
case kCircle:
drawCircle (shapes[i].bounds, shapes[i].fillColor);
break;
// case kRectangle:
// drawRectangle (shapes[i].bounds, shapes[i].fillColor);
// break;
// case kOblateSpheroid:
// drawEgg (shapes[i].bounds, shapes[i].fillColor);
// break;
}
}
}
int main(int argc, const char * argv[])
{
Shape shapes[3];
ShapeRect rect0 = {0, 0, 10, 30};
shapes[0].type = kCircle;
shapes[0].fillColor = kRedColor;
shapes[0].bounds = rect0;
// ShapeRect rect1 = {30, 40, 50, 60};
// shapes[1].type = kRectangle;
// shapes[1].fillColor = kGreenColor;
// shapes[1].bounds = rect1;
//
// ShapeRect rect2 = {15, 18, 37, 29};
// shapes[2].type = kOblateSpheroid;
// shapes[2].fillColor = kBlueColor;
// shapes[2].bounds = rect2;
drawShapes (shapes, 1);
return 0;
}
到OC~
//误报:Must explicitly describe intended ownership of an object array parameter。如果你看到了这个错误信息,你可以选中左边的项目名,然后再选中右边的PROJECT-->Apple LLVM compiler 4.2 - Language-->Objective-C Automatic Reference Counting,它本来的值是Yes,将它的值改为No,就可以正常编译运行了。
//#import <Foundation/Foundation.h>
//typedef enum{ kCircle, kRectangle, kOblateSpheroid}ShapeType;
//typedef enum{ kRedColor, kGreenColor, kBlueColor}ShapeColor;
//typedef struct {
// int x, y, width, height;
//}ShapeRect;
//typedef struct {
// ShapeType type;
// ShapeColor fillColor;
// ShapeRect bounds;
//}Shape;
//NSString *colorName (ShapeColor colorName)
//{
// switch (colorName)
// {
// case kRedColor:
// return @"red";
// break;
// case kGreenColor:
// return @"green";
// break;
// case kBlueColor:
// return @"blue";
// break;
// default:
// return @"No";
// break;
// }
//}
//
//@interface Circle : NSObject
//{
// ShapeColor fillColor;
// ShapeRect bounds;
//}
//- (void) setFillColor : (ShapeColor) fillColor;
//- (void) setBounds : (ShapeRect) bounds;
//- (void) draw;
//@end
//@implementation Circle
//- (void) setFillColor:(ShapeColor ) c
//{
// fillColor = c;
//}
//- (void) setBounds:(ShapeRect) b
//{
// bounds = b;
//}
//- (void) draw
//{
// NSLog(@"drawing a Circle (%d %d %d %d) in %@", bounds.x, bounds.y, bounds.width, bounds.height, colorName(fillColor));
//}
//@end
//
//void drawShapes (id shapes[], int count)
//{
// int i;
// for (i = 0; i < count; i++)
// {
// id shape = shapes[i];
// [shape draw];
// }
//}
//int main(int argc, const char * argv[])
//{
// id shapes[3];
//
// ShapeRect rect0 = {0, 0, 10, 30};
// shapes[0] = [Circle new];
// [shapes[0] setFillColor: kRedColor];
// [shapes[0] setBounds: rect0];
//
ShapeRect rect1 = {30, 40, 50, 60};
shapes[1] = [Rectangle new];
[shapes[1] setFillColor: kGreenColor];
[shapes[1] setBounds: rect1];
ShapeRect rect2 = {15, 19, 37, 29};
shapes[2] = [OblataSphereoid new];
[shapes[2] setFillColor: kBlueColor];
[shapes[2] setBounds: rect2];
//
// drawShapes (shapes, 1); //同样,只实现画圆
//
// return 0;
//}
C、完整的OC
#import <Foundation/Foundation.h>
typedef enum {kRedColor, kGreenColor, kBlueColor} ShapeColor;
typedef struct
{
int x, y, width, height;
} ShapeRect;
NSString *colorName (ShapeColor color)
{
NSString *colorName;
switch (color) {
case kRedColor:
colorName = @"red";
break;
case kGreenColor:
colorName = @"green";
break;
case kBlueColor:
colorName = @"blue";
break;
default:
colorName = @"Unexpected color";
break;
}
return (colorName);
} // colorName
@interface Shape : NSObject
{
ShapeColor fillColor;
ShapeRect bounds;
}
- (void) setFillColor: (ShapeColor) fillColor;
- (void) setBounds: (ShapeRect) bounds;
- (void) draw;
@end // Shape
@implementation Shape
- (void) setFillColor: (ShapeColor) c
{
fillColor = c;
} // setFillColor
- (void) setBounds: (ShapeRect) b
{
bounds = b;
} // setBounds
- (void) draw
{
} // draw
@end // Shape
@interface Triangle : Shape
@end // Triangle
@implementation Triangle
- (void) draw
{
NSLog (@"drawing a triangle at (%d %d %d %d) in %@",
bounds.x, bounds.y,
bounds.width, bounds.height,
colorName(fillColor));
} // draw
@end // Triangle
@interface Circle : Shape
@end // Circle
@implementation Circle
- (void) draw
{
NSLog (@"drawing a circle at (%d %d %d %d) in %@",
bounds.x, bounds.y,
bounds.width, bounds.height,
colorName(fillColor));
} // draw
@end // Circle
@interface Rectangle : Shape
@end // Rectangle
@implementation Rectangle
- (void) draw
{
NSLog (@"drawing a rectangle at (%d %d %d %d) in %@",
bounds.x, bounds.y,
bounds.width, bounds.height,
colorName(fillColor));
} // draw
@end // Rectangle
@interface OblateSphereoid : Shape
@end // OblateSphereoid
@implementation OblateSphereoid
- (void) draw
{
NSLog (@"drawing an egg at (%d %d %d %d) in %@",
bounds.x, bounds.y,
bounds.width, bounds.height,
colorName(fillColor));
} // draw
@end // OblateSphereoid
void drawShapes (id shapes[], int count) //选中项目名称—>右边的Build Settings 下拉找到Apple LLVM 5.1 - Language - Objective C ——>Objective-C Automatic Reference Counting,它本来的值是Yes,将它的值改为No,就可以正常编译运行了
{
for (int i = 0; i < count; i++)
{
id shape = shapes[i];
[shape draw];
}
} // drawShapes
int main (int argc, const char * argv[])
{
id shapes[4]; // I'm different!
ShapeRect rect0 = { 0, 0, 10, 30 };
shapes[0] = [Circle new];
[shapes[0] setBounds: rect0];
[shapes[0] setFillColor: kRedColor];
ShapeRect rect1 = { 30, 40, 50, 60 };
shapes[1] = [Rectangle new];
[shapes[1] setBounds: rect1];
[shapes[1] setFillColor: kGreenColor];
ShapeRect rect2 = { 15, 19, 37, 29 };
shapes[2] = [OblateSphereoid new];
[shapes[2] setBounds: rect2];
[shapes[2] setFillColor: kBlueColor];
ShapeRect rect3 = { 47, 32, 80, 50 }; // I'm new!
shapes[3] = [Triangle new];
[shapes[3] setBounds: rect3];
[shapes[3] setFillColor: kRedColor];
drawShapes (shapes, 4); // I'm different!
return (0);
} // main