封装
封装:隐藏内部(定义类、定义属性、定义方法。) 实现,稳定外部接口。
@propert
和@synthesize
#import “Car.h”
#import <Foundation/Foundation.h>
@interface Car : NSObject
{
int _wheels; //Car轮子属性
int _speed; //Car速度属性
}
@property int wheels,speed;
- (void) print;
@end
@property int wheels,speed;
- (void) setWheels:(int) wheels
{
_wheels = wheels;
}
- (int)wheels
{
return _wheels;
}
- (void) setSpeed:(int) speed
{
_speed = speed;
}
- (int)speed
{
return _speed;
}
@synthesize
实现类的setter
、getter
方法。代码如下。(在现在的Xcode中,可以省略,但不建议这样操作。)
#import "Car.h”
@implementation Car
@synthesize wheels =_wheels ,speed = _speed;
- (void) print
{
NSLog(@"bike的轮子数量为%i, 速度为%i !!!",_wheels,_speed);
}
@end
@synthesize wheels =_wheels ,speed = _speed;代码必须写@implementation和@end之间,此代码的的意思是将@property wheels,speed,进行实现,而wheels =_wheels ,speed = _speed是将访问方法实现里面_wheels和_speed的成员变量并进行给赋值。
#import "Car.h"
#import <Foundation/Foundation.h>
int main(int argc, const char * argv[])
{
Car *bike = [[Car alloc]init];
[bike setWheels:100];
[bike setSpeed:50];
[bike print];
return 0 ;
}
多态
抽象的打印机类Printer
Printer.h
#import @interface Printer : NSObject - (void) print; @end |
就是一个简单的方法print
Printer.m
#import "Printer.h" @implementation Printer - (void)print{ NSLog(@ "打印机打印纸张" ); } @end |
实现也是很简单的
下面来看一下具体的子类
ColorPrinter.h
#import "Printer.h" //修改父类的打印行为 @interface ColorPrinter : Printer - (void)print; @end |
ColorPrinter.m
#import "ColorPrinter.h" @implementation ColorPrinter - (void)print{ NSLog(@ "彩色打印机" ); } @end |
在看一下另外一个子类
BlackPrinter.h
BlackPrinter.m
#import "BlackPrinter.h"
@implementation BlackPrinter
- (void)print{ NSLog(@ "黑白打印机" ); }
@end |
这里我们在定义一个Person类,用来操作具体的打印机
Person.h
Person.m
#import "Person.h"
@implementation Person
/* - (void) printWithColor:(ColorPrinter *)colorPrint{ [colorPrint print]; }
- (void) printWithBlack:(BlackPrinter *)blackPrint{ [blackPrint print]; } */
- (void) doPrint:(Printer *)printer{ [printer print]; }
@end |
再来看一下测试代码:
main.m
// main.m
#import
#import "Person.h" #import "BlackPrinter.h" #import "ColorPrinter.h"
int main(int argc, const charchar * argv[]) { @autoreleasepool {
Person *person =[[Person alloc] init];
ColorPrinter *colorPrint = [[ColorPrinter alloc] init]; BlackPrinter *blackPrint = [[BlackPrinter alloc] init];
//多态的定义 /* Printer *p1 = [[ColorPrinter alloc] init]; Printer *p2 = [[BlackPrinter alloc] init];
[person doPrint:p1]; [person doPrint:p2]; */
//通过控制台输入的命令来控制使用哪个打印机 int cmd; do { scanf( "%d" ,&cmd); if (cmd == 1){ [person doPrint:colorPrint]; } else if (cmd == 2){
[person doPrint:blackPrint]; } } while (1);
} return 0;
} |
下面就来详细讲解一下多态的好处
上面的例子是一个彩色打印机和黑白打印机这两种打印机,然后Person类中有一个操作打印的方法,当然这个方法是需要打印机对象的,如果不用多态机制实现的话(Person.h中注释的代码部分),就是给两种打印机单独定义个操作的方法,然后在Person.m(代码中注释的部分)中用具体的打印机对象进行操作,在main.m文件中,我们看到,当Person需要使用哪个打印机的时候,就去调用指定的方法:
1
2
|
[person printWithBlack:blackPrint]; //调用黑白打印机 [person printWithColor:colorPrint]; //调用彩色打印机 |
这种设计就不好了,为什么呢?假如现在又有一种打印机,那么我们还需要在Person.h中定义一种操作这种打印机的方法,那么后续如果在添加新的打印机呢?还在添加方法吗?那么Person.h文件就会变得很臃肿。所以这时候多态就体现到好处了,使用父类类型,在Person.h中定义一个方法就可以了:
1
|
- (void) doPrint:(Printer *)printer; |
这里看到了,这个方法的参数类型就是父类的类型,这就是多态,定义类型为父类类型,实际类型为子类类型
1
2
3
|
- (void) doPrint:(Printer *)printer{ [printer print]; } |
这里调用print方法,就是传递进来的实际类型的print方法。
1
2
3
4
5
|
Printer *p1 = [[ColorPrinter alloc] init]; Printer *p2 = [[BlackPrinter alloc] init];
[person doPrint:p1]; [person doPrint:p2]; |