05-面向对象三大特点:封装、继承、多态

一、        封装(设置器set和构造器get)

1.      set方法和get方法

  •  set方法和get方法的使用场合

 

@public的成员可以被随意赋值,应该使用set方法和get方法来管理成员的访问(类似机场的安检、水龙头过滤,过滤掉不合理的东西),比如僵尸的生命值不能为负数

  •   set方法

1).作用:提供一个方法给外界设置成员变量值,可以在方法里面对参数进行相应过滤

2).命名规范:

 1> 方法名必须以set开头

 2> set后面跟上成员变量的名称,成员变量的首字母必须大写

 3> 返回值一定是void

 4> 一定要接收一个参数,而且参数类型跟成员变量类型一致

 5> 形参的名称不能跟成员变量名一样

  •    get方法

1).作用:返回对象内部的成员变量

2).命名规范:

 1> 肯定有返回值,返回值类型肯定与成员变量类型一致

 2> 方法名跟成员变量名一样

 3> 不需要接收任何参数

 

  •   成员变量的命名规范

 

  1>.成员变量都以下划线 _ 开头

  2>.可以跟get方法的名称区分开

  3>.可以跟其他局部变量区分开,一看到下划线开头的变量,肯定是成员变量

  •    代码示例

 1 #import <Foundation/Foundation.h>
 2 // 声明
 3 @interface Student : NSObject
 4 {
 5     int _age; // 学生的年龄
 6 }
 7 /*set方法*/
 8 - (void)setAge:(int)age;
 9 /*get方法*/
10 - (int)age;
11 @end
12 
13 @implementation Student
14 // set方法的实现
15 - (void)setAge:(int)age
16 {
17     // 对外面传进来的年龄进行一下过滤
18     if (age<=0) {
19         age = 1;
20     }
21     _age = age;
22 }
23 
24 // get方法的实现
25 - (int)age
26 {
27     return _age;
28 }
29 
30 @end
View Code

 

2.      类方法

  •    基本概念

直接可以用类名来执行的方法(类本身会在内存中占据存储空间,里面有类\对象方法列表)

  •   类方法和对象方法对比

1)   对象方法

  • 以减号-开头
  • 只能让对象调用,没有对象,这个方法根本不可能被执行
  • 对象方法能访问实例变量(成员变量)

 

2)   类方法

  • 以加号+开头
  • 只能用类名调用,对象不能调用
  • 类方法中不能访问实例变量(成员变量)
  • 使用场合:当不需要访问成员变量的时候,尽量用类方法

3)       类方法和对象方法可以同名

  •    示例

/*
 设计一个计算器类
 * 求和
 * 求平均值
 */

#import <Foundation/Foundation.h>

// 工具类:基本没有任何成员变量,里面的方法基本都是类方法
@interface JiSusnQi : NSObject
+ (int)sumOfNum1:(int)num1 andNum2:(int)num2;

+ (int)averageOfNum1:(int)num1 andNum2:(int)num2;
@end

@implementation JiSusnQi
+ (int)sumOfNum1:(int)num1 andNum2:(int)num2
{
    return num1 + num2;
}

+ (int)averageOfNum1:(int)num1 andNum2:(int)num2
{
    // 在这种情况下,self代表类
    int sum = [self sumOfNum1:num1 andNum2:num2];
    return sum / 2;
}
@end

int main()
{
    int a = [JiSusnQi averageOfNum1:10 andNum2:12]; 
    NSLog(@"a=%d", a); 
    return 0;
}
计算器类

3.      self关键字

  •    成员变量和局部变量同名

  • 当成员变量和局部变量同名时,采取就近原则,访问的是局部变量
  • 用self访问成员变量,区分同名的局部变量
  •    使用细节

1)    出现的地方:所有的OC方法中(对象方法\类方法),不能出现在函数

2)    作用

 self的用途:

 1> 谁调用了当前方法,self就代表谁

      self出现在对象方法中,self就代表对象

      self出现在类方法中,self就代表类

 

 2> 在对象方法利用"self->成员变量名"访问当前对象内部的成员变量

 

 3> [self 方法名]可以调用其他对象方法\类方法

  • 设计Car类,一个对象方法跟其他车子比较车速,返回速度差,一个类方法比较两辆车的车速,返回速度差
  •    常见错误

  • 使用 "self->成员变量名" 访问当前方法调用的成员变量
  • 使用 "[self 方法名];" 来调用方法(对象方法\类方法)
  • 低级错误:用self去调用函数
  • 类方法中用self调用对象方法,对象方法中用self调用类方法
  • self死循环
  •    示例

 1 /**
 2  4.设计Car类
 3  1> 属性
 4  * 速度
 5  
 6  2> 方法
 7  * 属性相应的set和get方法
 8  * 一个对象方法跟其他车子比较车速,返回速度差
 9  * 一个类方法比较两辆车的车速,返回速度差
10  */
11 
12 #import <Foundation/Foundation.h>
13 
14 //
15 @interface Car : NSObject
16 {
17     int _speed; // 速度
18 }
19 
20 // 速度的getter和setter
21 - (void)setSpeed:(int)speed;
22 - (int)speed;
23 
24 // 跟其他车子比较车速,返回速度差
25 - (int)compareSpeedWithOther:(Car *)car;
26 // 比较两辆车的车速,返回速度差
27 + (int)compareSpeedBetweenCar1:(Car *)car1 andCar2:(Car *)car2;
28 @end
29 
30 @implementation Car
31 // 速度的getter和setter
32 - (void)setSpeed:(int)speed
33 {
34     _speed = speed;
35 }
36 - (int)speed
37 {
38     return _speed;
39 }
40 
41 // 跟其他车子比较车速,返回速度差
42 - (int)compareSpeedWithOther:(Car *)car
43 {
44     // 第1种思路
45     // return _speed - [car speed];
46     
47     // 第2种思路
48     return [Car compareSpeedBetweenCar1:self andCar2:car];
49 }
50 
51 // 比较两辆车的车速,返回速度差
52 + (int)compareSpeedBetweenCar1:(Car *)car1 andCar2:(Car *)car2
53 {
54     return [car1 speed] - [car2 speed];
55 }
56 @end
设计Car类

 

 

二、        继承

1.     继承的基本用法

  1 // Bird的声明
  2 
  3 @interface Bird : NSObject
  4 
  5 {
  6 
  7     @public
  8 
  9     int weight;
 10 
 11 }
 12 
 13 - (void)eat;
 14 
 15 @end
 16 
 17 // Bird的定义
 18 
 19 @implementation Bird
 20 
 21 - (void)eat {
 22 
 23     NSLog(@"吃吃吃-体重:%d", weight);
 24 
 25 }
 26 
 27 @end
 28 
 29 // Dog的声明
 30 
 31 @interface Dog : NSObject
 32 
 33 {
 34 
 35     @public
 36 
 37     int weight;
 38 
 39 }
 40 
 41 - (void)eat;
 42 
 43 @end
 44 
 45 // Dog的定义
 46 
 47 @implementation Dog
 48 
 49 - (void)eat {
 50 
 51     NSLog(@"吃吃吃-体重:%d", weight);
 52 
 53 }
 54 
 55 @end
 56 
 57 l   有相同的属性和行为,抽出一个父类Animal(先抽取weight属性,再抽取eat方法)
 58 
 59 // Animal的声明
 60 
 61 @interface Animal : NSObject
 62 
 63 {
 64 
 65     @public
 66 
 67         int weight;
 68 
 69 }
 70 
 71 - (void)eat;
 72 
 73 @end
 74 
 75 // Animal的定义
 76 
 77 @implementation Animal
 78 
 79 - (void)eat {
 80 
 81     NSLog(@"吃吃吃-体重:%d", weight);
 82 
 83 }
 84 
 85 @end
 86 
 87 l   子类在父类的基础上拓充属性和方法
 88 
 89 // Bird的声明
 90 
 91 @interface Bird : Animal
 92 
 93 {
 94 
 95     @public
 96 
 97         int height;
 98 
 99 }
100 
101 - (void)fly;
102 
103 @end
104 
105  
106 
107 // Bird的定义
108 
109 @implementation Bird
110 
111 - (void)fly {
112 
113     NSLog(@"飞飞飞-高度:%d", height);
114 
115 }
116 
117 @end
118 
119  
120 
121 // Dog的声明
122 
123 @interface Dog : Animal
124 
125 {
126 
127     @public
128 
129         int speed;
130 
131 }
132 
133 - (void)run;
134 
135 @end
136 
137 // Dog的定义
138 
139 @implementation Dog
140 
141 - (void)run {
142 
143     NSLog(@"跑跑跑-高度:%d", speed);
144 
145 }
146 
147 @end
设计两个类Bird、Dog

 

  •    子类方法和属性的访问过程:如果子类没有,就去访问父类的
  •    父类被继承了还是能照常使用的
  •    父类的静态方法
  •    画继承结构图,从子类抽取到父类
  •    NSObject的引出:全部OC类的最终父类,包含了一些常用方法,比如+new

 

2.     继承的专业术语

  •   父类\超类  superclass
  •    子类  subclass\subclasses

3.     继承的细节

  •    单继承
  •    子类和父类不能有相同的成员变量
  •    方法的重写

 

4.     super关键字

  •    分别调用父类的对象方法和类方法

5.     继承的好处

  •    不改变原来模型的基础上,拓充方法
  •    建立了类与类之间的联系
  •    抽取了公共代码
  •    坏处:耦合性强

6.     继承的使用场合

  •    它的所有属性都是你想要的,一般就继承
  •    它的部分属性是你想要的,可以抽取出另一个父类

 

三、        多态

1.多态的基本概念

  •    某一类事物的多种形态
  •    OC对象具有多态性 

2.多态的体现

Person *p = [Student new];  // 多态的条件: 有继承关系,有方法的重写,父类的声明变量指向子类对象

p->age = 100;

[p walk];

  •    子类对象赋值给父类指针
  •    父类指针访问对应的属性和方法

 

3.多态的好处

  •    用父类接收参数,节省代码

 

4.多态的局限性

  •    不能访问子类的属性(可以考虑强制转换)

 

5.多态的细节

  •    动态绑定:在运行时根据对象的类型确定动态调用的方法

 

 

posted on 2014-04-23 22:47  ゴルツの惠斌纳閣下  阅读(184)  评论(0)    收藏  举报