• OC 设计模式


             设计模式

             一种或几种被所有程序员广泛认同的,有某些特定功能,或者实现某些特殊作用的编码格式

             单例模式

             键值编码(KVC)

             键值观察(KVO)

             观察者模式()

             工厂模式(工厂方法)

             ps:MVC && MVVM && CVC

    一、单例模式

     1 #import <Foundation/Foundation.h>
     2 
     3 /*
     4  单例模式
     5  1.通常情况下,一个工程只有一个单例类。
     6  2.我们将一个类选中,将它作为单例类。
     7  3.在整个工程中这个类所创建的对象是唯一并且不能被释放
     8  
     9  作用:界面传值-在整个工程任意位置对单例对象的属性进行赋值
    10               也可以在整个工程的任意位置对单例对象的属性进行访问
    11  */
    12 @interface Globle : NSObject
    13 
    14 @property (strong, nonatomic) NSString *userId;
    15 
    16 // 单例方法
    17 // 作用:获取唯一单例对象
    18 + (Globle*) shareGloble;//getGloble
    19 
    20 @end
    21 
    22 #import "Globle.h"
    23 
    24 // 创建一个单例对象,用静态修饰符将这个对象的生命周期延长至整个工程
    25 static Globle *globle = nil;
    26 
    27 @implementation Globle
    28 
    29 +(Globle *)shareGloble
    30 {
    31     // 第一次执行单例方法,将单例对象初始化
    32     if (globle == nil) {
    33         globle = [[Globle alloc] init];
    34         globle.userId = @"";
    35     }
    36     // 之后的每次调用,都会直接返回上面的唯一单例对象
    37     return globle;
    38 }
    39 @end
    40 
    41 
    42 #import <Foundation/Foundation.h>
    43 #import "Globle.h"
    44 
    45 @interface People : NSObject
    46 
    47 +(void) showUserId;
    48 
    49 @end
    50 
    51 #import "People.h"
    52 
    53 @implementation People
    54 
    55 +(void)showUserId
    56 {
    57     NSLog(@"userId:%@",[Globle shareGloble].userId);
    58 }
    59 @end
    60 
    61 
    62 #import <Foundation/Foundation.h>
    63 #import "Globle.h"
    64 #import "People.h"
    65 
    66 int main(int argc, const char * argv[]) {
    67     @autoreleasepool {
    68 
    69         [Globle shareGloble].userId = @"1001";
    70         [People showUserId];
    71 
    72     }
    73     return 0;
    74 }

    二、KVC

     1 #import <Foundation/Foundation.h>
     2 
     3 /*
     4  KVC key-value-coding
     5  
     6  作用:能够无视OC中关于私有的设定,直接通过底层赋值方式对属性赋值(和获取);
     7  
     8  */
     9 @interface KVCClass : NSObject
    10 
    11 -(void) showProperty;
    12 
    13 @end
    14 
    15 #import "KVCClass.h"
    16 #import "Student.h"
    17 
    18 @interface KVCClass ()
    19 
    20 @property (strong, nonatomic) NSString  *kvcProperty;
    21 @property (strong, nonatomic) Student *tempStu;
    22 
    23 @end
    24 
    25 @implementation KVCClass
    26 
    27 - (instancetype)init
    28 {
    29     self = [super init];
    30     if (self) {
    31         self.tempStu =[[Student alloc] init];
    32     }
    33     return self;
    34 }
    35 
    36 -(void)showProperty
    37 {
    38     NSLog(@"property:%@",self.kvcProperty);
    39     NSLog(@"property:%@",self.tempStu.name);
    40 
    41 }
    42 @end
    43 
    44 
    45 #import <Foundation/Foundation.h>
    46 
    47 @interface Student : NSObject
    48 
    49 @property (strong, nonatomic) NSString *name;
    50 
    51 @end
    52 
    53 #import "Student.h"
    54 
    55 @implementation Student
    56 
    57 @end
    58 
    59 
    60 #import <Foundation/Foundation.h>
    61 
    62 #import "KVCClass.h"
    63 int main(int argc, const char * argv[]) {
    64     @autoreleasepool {
    65         KVCClass *kvc = [[KVCClass alloc] init];
    66         
    67         //表示 在KVC对象中查找名字为[kvcProperty] 的属性,并对这个属性赋值为@“bowen”
    68         // 设置
    69         [kvc setValue:@"bowen" forKey:@"kvcProperty"];
    70         
    71         [kvc setValue:@"bowen1" forKeyPath:@"tempStu.name"];
    72         
    73         [kvc showProperty];
    // 取值

                 NSLog(@"%@",[kvc valueForKey:@"kvcProperty"]);

    74         NSLog(@"%@",[kvc valueForKeyPath:@"tempStu.name"]);
    75     }
    76     return 0;
    77 }

    OC中的KVC操作就和Java中使用反射机制去访问类的private权限的变量,很暴力的,这样做就会破坏类的封装性,本来类中的的private权限就是不希望外界去访问的,但是我们这样去操作,就会反其道而行,但是我们有时候真的需要去这样做,哎。所以说有些事不是都是顺其自然的,而是需要的时候自然就诞生了。

    下面就来看一下这种技术的使用:

    Dog.h

    1. //  
    2. //  Dog.h  
    3. //  42_KVC  
    4. //  
    5. //  Created by jiangwei on 14-10-14.  
    6. //  Copyright (c) 2014年 jiangwei. All rights reserved.  
    7. //  
    8.   
    9. #import <Foundation/Foundation.h>  
    10.   
    11. @interface Dog : NSObject  
    12.   
    13. @end  

    Dog.m

    1. //  
    2. //  Dog.m  
    3. //  42_KVC  
    4. //  
    5. //  Created by jiangwei on 14-10-14.  
    6. //  Copyright (c) 2014年 jiangwei. All rights reserved.  
    7. //  
    8.   
    9. #import "Dog.h"  
    10.   
    11. @implementation Dog  
    12.   
    13. @end  

    定义了Dog这个类,但是什么都没有,他只是一个中间类,没什么作用,在这个demo中。

    Person.h

    1. //  
    2. //  Person.h  
    3. //  42_KVC  
    4. //  
    5. //  Created by jiangwei on 14-10-14.  
    6. //  Copyright (c) 2014年 jiangwei. All rights reserved.  
    7. //  
    8.   
    9. #import <Foundation/Foundation.h>  
    10. #import "Dog.h"  
    11.   
    12. @interface Person : NSObject{  
    13. @private  
    14.     NSString *_name;  
    15.     NSDog *_dog;  
    16.       
    17.     NSInteger *age;  
    18. }  
    19.   
    20. @end  

    Person.m

    1. //  
    2. //  Person.m  
    3. //  42_KVC  
    4. //  
    5. //  Created by jiangwei on 14-10-14.  
    6. //  Copyright (c) 2014年 jiangwei. All rights reserved.  
    7. //  
    8.   
    9. #import "Person.h"  
    10.   
    11. @implementation Person  
    12.   
    13. - (NSString *)description{  
    14.     NSLog(@"%@",_name);  
    15.     return _name;  
    16. }  
    17.   
    18. @end  

    Person类中我们定义了两个属性,但是这两个属性对外是不可访问的,而且也没有对应的get/set方法。我们也实现了description方法,用于打印结果

    看一下测试代码

    main.m

    1. //  
    2. //  main.m  
    3. //  42_KVC  
    4. //  
    5. //  Created by jiangwei on 14-10-14.  
    6. //  Copyright (c) 2014年 jiangwei. All rights reserved.  
    7. //  
    8.   
    9. #import <Foundation/Foundation.h>  
    10. #import "Person.h"  
    11. #import "Dog.h"  
    12.   
    13. //KVC:很暴力,及时一个类的属性是私有的,而且也没有get/set方法,同样可以读写  
    14. //相当于Java中的反射,破坏类的封装性  
    15. int main(int argc, const charchar * argv[]) {  
    16.     @autoreleasepool {  
    17.           
    18.         Person *p = [[Person alloc] init];  
    19.           
    20.         //设置值  
    21.         //这里setValue方法:第一个参数是value,第二个参数是key(就是类的属性名称)  
    22.         [p setValue:@"jiangwei" forKey:@"name"];  
    23.           
    24.         Dog *dog = [[Dog alloc] init];  
    25.         [p setValue:dog forKey:@"dog"];  
    26.           
    27.         //KVC设置值时,如果属性有set方法,则优先调用set方法,如果没有则直接设置上去,get方法类似  
    28.           
    29.         //读取值  
    30.         NSString *name = [p valueForKey:@"name"];  
    31.           
    32.         //设置基本数据类型  
    33.         //这里需要将基本类型转化成NSNumber  
    34.         //在设置值的时候,会有自动解包的过程,NSNumber会解包赋值给age  
    35.         [p setValue:@22 forKey:@"age"];  
    36.           
    37.         NSLog(@"%@",p);  
    38.           
    39.         return 0;  
    40.     }  
    41.     return 0;  
    42. }  

    这里我们生成一个Person对象,然后开始使用KVC技术了:

    1、设置属性值

    1. //设置值  
    2. //这里setValue方法:第一个参数是value,第二个参数是key(就是类的属性名称)  
    3. [p setValue:@"jiangwei" forKey:@"name"];  
    4.           
    5. Dog *dog = [[Dog alloc] init];  
    6. [p setValue:dog forKey:@"dog"];  

    使用setValue方法,就可以进行对属性进行设置值操作了,同时需要传递这个属性的名称,这个和Java中使用反射机制真的很像。

    注:KVC设置值时,如果属性有set方法,则优先调用set方法,如果没有则直接设置上去,get方法一样

     

    1. //设置基本数据类型  
    2. //这里需要将基本类型转化成NSNumber  
    3. //在设置值的时候,会有自动解包的过程,NSNumber会解包赋值给age  
    4. [p setValue:@22 forKey:@"age"];  

    还有一个需要注意的地方:当我们在设置基本类型的时候,需要将其转化成NSNumber类型的。

    2、取属性的值

     

    1. //读取值  
    2. NSString *name = [p valueForKey:@"name"];  

    取值就简单了

     

    下面再来看一下KVC中强大的功能:键值路径

    键值路径是对于一个类中有数组对象的属性进行便捷操作。

    看个场景:

    一个作者有多本书

    Author.h

     

    1. //  
    2. //  Author.h  
    3. //  43_KeyValuePath  
    4. //  
    5. //  Created by jiangwei on 14-10-15.  
    6. //  Copyright (c) 2014年 jiangwei. All rights reserved.  
    7. //  
    8.   
    9. #import <Foundation/Foundation.h>  
    10.   
    11. @interface Author : NSObject{  
    12.     NSString *_name;  
    13.       
    14.     //作者出版的书,一个作者对应多个书籍对象  
    15.     NSArray *_issueBook;  
    16. }  
    17.   
    18. @end  

    作者类中定义了名字和一个书籍数组

     

    Author.m

     

    1. //  
    2. //  Author.m  
    3. //  43_KeyValuePath  
    4. //  
    5. //  Created by jiangwei on 14-10-15.  
    6. //  Copyright (c) 2014年 jiangwei. All rights reserved.  
    7. //  
    8.   
    9. #import "Author.h"  
    10.   
    11. @implementation Author  
    12.   
    13. @end  

     

    Book.h

     

    1. //  
    2. //  Book.h  
    3. //  43_KeyValuePath  
    4. //  
    5. //  Created by jiangwei on 14-10-15.  
    6. //  Copyright (c) 2014年 jiangwei. All rights reserved.  
    7. //  
    8.   
    9. #import <Foundation/Foundation.h>  
    10. #import "Author.h"  
    11.   
    12. @interface Book : NSObject{  
    13.     Author *_author;  
    14. }  
    15.   
    16. @property NSString *name;  
    17. @property floatfloat *price;  
    18.   
    19. @end  

    定义了一个作者属性,书的名字,价格

     

    Book.m

     

    1. //  
    2. //  Book.m  
    3. //  43_KeyValuePath  
    4. //  
    5. //  Created by jiangwei on 14-10-15.  
    6. //  Copyright (c) 2014年 jiangwei. All rights reserved.  
    7. //  
    8.   
    9. #import "Book.h"  
    10.   
    11. @implementation Book  
    12.   
    13. @end  


    看一下测试代码

    main.m

     

    1. //  
    2. //  main.m  
    3. //  43_KeyValuePath  
    4. //  
    5. //  Created by jiangwei on 14-10-15.  
    6. //  Copyright (c) 2014年 jiangwei. All rights reserved.  
    7. //  
    8.   
    9. #import <Foundation/Foundation.h>  
    10. #import "Book.h"  
    11. #import "Author.h"  
    12.   
    13. int main(int argc, const charchar * argv[]) {  
    14.     @autoreleasepool {  
    15.           
    16.         //------------------KVC键值路径  
    17.         /* 
    18.         Book *book = [[Book alloc] init]; 
    19.         Author *author = [[Author alloc] init]; 
    20.          
    21.         //设置作者 
    22.         [book setValue:author forKey:@"author"]; 
    23.          
    24.         //设置作者的名字 
    25.         //路径为:author.name,中间用点号进行连接 
    26.         [book setValue:@"jiangwei" forKeyPath:@"author.name"]; 
    27.         NSString *name = [author valueForKey:@"name"]; 
    28.         NSLog(@"name is %@",name); 
    29.          */  
    30.           
    31.           
    32.         //--------------------KVC的运算  
    33.         Author *author = [[Author alloc] init];  
    34.         [author setValue:@"莫言" forKeyPath:@"name"];  
    35.           
    36.         Book *book1 = [[Book alloc] init];  
    37.         book1.name = @"红高粱";  
    38.         book1.price = 9;  
    39.         Book *book2 = [[Book alloc] init];  
    40.         book2.name = @"蛙";  
    41.         book2.price = 10;  
    42.         NSArray *array = [NSArray arrayWithObjects:book1,book2, nil nil];  
    43.         [author setValue:array forKeyPath:@"issueBook"];  
    44.           
    45.         //基本数据类型会自动被包装成NSNumber,装到数组中  
    46.         //得到所有书籍的价格  
    47.         NSArray *priceArray = [author valueForKeyPath:@"issueBook.price"];  
    48.         NSLog(@"%@",priceArray);  
    49.           
    50.         //获取数组的大小  
    51.         NSNumber *count = [author valueForKeyPath:@"issueBook.@count"];  
    52.         NSLog(@"count=%@",count);  
    53.           
    54.         //获取书籍价格的总和  
    55.         NSNumber *sum = [author valueForKeyPath:@"issueBook.@sum.price"];  
    56.         NSLog(@"%@",sum);  
    57.           
    58.         //获取书籍的平均值  
    59.         NSNumber *avg = [author valueForKeyPath:@"issueBook.@avg.price"];  
    60.         NSLog(@"%@",avg);  
    61.           
    62.         //获取书籍的价格最大值和最小值  
    63.         NSNumber *max = [author valueForKeyPath:@"issueBook.@max.price"];  
    64.         NSNumber *min = [author valueForKeyPath:@"issueBook.@min.price"];  
    65.           
    66.     }  
    67.     return 0;  
    68. }  

     

    1、首先通过前面说到的KVC设置作者的书籍数组

     

    1. //--------------------KVC的运算  
    2. Author *author = [[Author alloc] init];  
    3. [author setValue:@"莫言" forKeyPath:@"name"];  
    4.   
    5. Book *book1 = [[Book alloc] init];  
    6. book1.name = @"红高粱";  
    7. book1.price = 9;  
    8. Book *book2 = [[Book alloc] init];  
    9. book2.name = @"蛙";  
    10. book2.price = 10;  
    11. NSArray *array = [NSArray arrayWithObjects:book1,book2, nil nil];  
    12. [author setValue:array forKeyPath:@"issueBook"];  

    添加了两本书籍

     

    2、下面就开始用到KVC中键值路径了

    1)获取作者类中书籍数组中所有书籍的价格

     

    1. //基本数据类型会自动被包装成NSNumber,装到数组中  
    2. //得到所有书籍的价格  
    3. NSArray *priceArray = [author valueForKeyPath:@"issueBook.price"];  
    4. NSLog(@"%@",priceArray);  

    看到了:@"issueBook.price" 这就是键值路径的使用,issueBook是作者类中的书籍数组属性名,price是书籍类的属性,中间用点号进行连接,这样我们就可以获取到了所有书籍的价格了,如果在Java中,我们需要用一个循环操作。但是OC中多么方便。

     

    2)获取作者类中书籍数组的大小

     

    1. //获取数组的大小  
    2. NSNumber *count = [author valueForKeyPath:@"issueBook.@count"];  
    3. NSLog(@"count=%@",count);  

    使用 @"issueBook.@count" 键值路径获取书籍数组的大小,issueBook是作者类中的书籍数组属性名,@count是特定一个写法,可以把它想象成一个方法,中间任然用点号进行连接

     

    3)获取作者类中书籍数组的价格总和

    1. //获取书籍价格的总和  
    2. NSNumber *sum = [author valueForKeyPath:@"issueBook.@sum.price"];  
    3. NSLog(@"%@",sum);  

    使用 @"issueBook.@sum.price" 键值路径获取书籍数组中的价格总和,issueBook是作者类中的书籍数组属性名,@sum是特性写法,可以把它想象成一个方法,price是书籍的价格属性名,可以把它看成是@sum的一个参数,中间用点号进行连接

    如果在java中,这个需要用一个循环来计算总和,OC中很方便的

     

    4)获取作者类中书籍数组的价格平均值、最小值、最大值

    1. //获取书籍的平均值  
    2. NSNumber *avg = [author valueForKeyPath:@"issueBook.@avg.price"];  
    3. NSLog(@"%@",avg);  
    4.   
    5. //获取书籍的价格最大值和最小值  
    6. NSNumber *max = [author valueForKeyPath:@"issueBook.@max.price"];  
    7. NSNumber *min = [author valueForKeyPath:@"issueBook.@min.price"];  

    操作和上面类似,这里就不解释了

     

    我们看到上面返回来的数据都是NSNumber类型的

    三、观察者模式

     1 #import <Foundation/Foundation.h>
     2 
     3 /*
     4  观察者模式(通知模式)NSNotification
     5  观察者中心          NSNotificationCenter
     6  
     7  注册观察者必需在[发出通知]之前
     8  
     9  */
    10 
    11 @interface House : NSObject
    12 
    13 -(void) burn;
    14 
    15 @end
    16 
    17 #import "House.h"
    18 
    19 @implementation House
    20 
    21 -(void)burn
    22 {
    23     NSLog(@"房子着火了");
    24     // 发出通知
    25     [[NSNotificationCenter defaultCenter] postNotificationName:@"PlanB" object:nil];
    26 }
    27 @end
    28 
    29 #import <Foundation/Foundation.h>
    30 
    31 @interface Child : NSObject
    32 
    33 -(void) loudSay;
    34 
    35 -(void) toBeAGuanChazhe;
    36 
    37 @end
    38 
    39 #import "Child.h"
    40 
    41 @implementation Child
    42 
    43 -(void) loudSay
    44 {
    45     NSLog(@"报告:房子着火了");
    46 }
    47 
    48 -(void)toBeAGuanChazhe
    49 {
    50     // 创建观察者
    51     [[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(loudSay) name:@"PlanB" object:nil];
    52 }
    53 @end
    54 
    55 #import <Foundation/Foundation.h>
    56 
    57 #import "House.h"
    58 #import "Child.h"
    59 
    60 
    61 int main(int argc, const char * argv[]) {
    62     @autoreleasepool {
    63 
    64         House *myhouse = [[House alloc] init];
    65         
    66         Child *mychild = [[Child alloc] init];
    67         
    68         // 让mychild 成为观察者
    69         [mychild toBeAGuanChazhe];
    70         
    71         // 让房子着火,发出PlanB现象
    72         [myhouse burn];
    73     }
    74     return 0;
    75 }

    四、KVO

     1 #import <Foundation/Foundation.h>
     2 #import "JieCao.h"
     3 
     4 /*
     5  KVO key-value-observer(键值观察)
     6  
     7  作用:能够在被观察的某个属性发生变化的时候,自动执行某些方法
     8  
     9  当被观察的某个属性发生变化的时候,这个方法被自动回调
    10  
    11  -(void) observer...
    12  
    13  pss:当键值观察的观察者被使用完毕之后必须注销
    14  psss:键值观察是在[某个类中]给[某个属性] 注册观察者,当这个属性的值发生变化后作出响应模式
    15  
    16  */
    17 
    18 @interface Bowen : NSObject
    19 
    20 @property (strong,nonatomic) JieCao *my_jieCao;
    21 
    22 @end
    23 
    24 
    25 #import "Bowen.h"
    26 
    27 @implementation Bowen
    28 
    29 -(void) setMy_jieCao:(JieCao *)my_jieCao
    30 {
    31     _my_jieCao = my_jieCao;
    32     
    33     //注册观察者,观察_my_jieCao属性的值的变化
    34     [_my_jieCao addObserver:self forKeyPath:@"jieCaoValue" options:NSKeyValueObservingOptionNew context:nil];
    35     
    36 }
    37 // 不管在一个类当中注册一个多少KVO的观察者,本方法只能写一个
    38 -(void) observeValueForKeyPath:(NSString *)keyPath ofObject:(id)object change:(NSDictionary *)change context:(void *)context
    39 {
    40     if ([keyPath isEqualToString:@"jieCaoValue"]) {
    41         
    42         if ([[change objectForKey:@"new"] integerValue]<10) {
    43             NSLog(@"我要吐了,受不了老师了");
    44         }
    45 //        NSLog(@"keyPath:%@",keyPath);
    46 //        NSLog(@"Object:%@",keyPath);
    47 //        NSLog(@"change:%@",[change objectForKey:@"new"]);
    48 
    49     }
    50 }
    51 - (void)dealloc
    52 {
    53     [_my_jieCao removeObserver:self forKeyPath:@"jieCaoValue"];
    54 }
    55 
    56 @end
    57 
    58 #import <Foundation/Foundation.h>
    59 
    60 @interface JieCao : NSObject
    61 
    62 @property (assign, nonatomic) NSInteger jieCaoValue;
    63 
    64 @end
    65 
    66 #import "JieCao.h"
    67 
    68 @implementation JieCao
    69 
    70 @end
    71 
    72 #import <Foundation/Foundation.h>
    73 
    74 #import "Bowen.h"
    75 #import "JieCao.h"
    76 
    77 int main(int argc, const char * argv[]) {
    78     @autoreleasepool {
    79         // 创建被观察属性
    80         JieCao *jieCao = [[JieCao alloc] init];
    81         jieCao.jieCaoValue = 100;
    82         // 创建观察对象
    83         Bowen *bowen = [[Bowen alloc] init];
    84         // 让观察对象开始观察[被观察属性]
    85         bowen.my_jieCao = jieCao;
    86         // 让被观察属性发生变化
    87         bowen.my_jieCao.jieCaoValue = 9;
    88     }
    89     return 0;
    90 }

    五、工厂模式

      1 #import <Foundation/Foundation.h>
      2 #import "Fruit.h"
      3 
      4 /*
      5  
      6  工厂模式:(工厂方法)
      7  
      8  个人理解:实际上就是用来快速大批量生产对象的
      9  
     10  优点:能够将原本在本类初始化的对象,延时到子类中去初始化。实现了一个开放封闭原则。
     11  
     12  */
     13 
     14 @interface FruitFactory : NSObject
     15 
     16 // 通过外部输入的名字,创建[名字对应的类] 的对象
     17 + (Fruit *)createFruitByName:(NSString *) name;
     18 
     19 @end
     20 
     21 #import "FruitFactory.h"
     22 
     23 @implementation FruitFactory
     24 
     25 +(Fruit *)createFruitByName:(NSString *)name
     26 {
     27     //需要知道名字对应的类
     28     Class class = NSClassFromString(name);
     29     // 创建想要的类对象
     30     Fruit *fruit = [[class alloc] init];
     31     // 返回新建的[想要的类]的对象
     32     return fruit;
     33 }
     34 @end
     35 
     36 
     37 #import <Foundation/Foundation.h>
     38 
     39 @interface Fruit : NSObject
     40 
     41 -(void) show;
     42 
     43 @end
     44 
     45 #import "Fruit.h"
     46 
     47 @implementation Fruit
     48 
     49 -(void)show
     50 {
     51     NSLog(@"I'm fruit");
     52 }
     53 @end
     54 
     55 #import "Fruit.h"
     56 
     57 @interface Apple : Fruit
     58 
     59 @end
     60 
     61 
     62 #import "Apple.h"
     63 
     64 @implementation Apple
     65 
     66 -(void)show
     67 {
     68     NSLog(@"I'm apple");
     69 }
     70 
     71 
     72 #import "Fruit.h"
     73 
     74 @interface Banana : Fruit
     75 
     76 @end
     77 
     78 #import "Banana.h"
     79 
     80 @implementation Banana
     81 
     82 -(void)show
     83 {
     84     NSLog(@"I'm banana");
     85 }
     86 
     87 @end
     88 
     89 #import "Fruit.h"
     90 
     91 @interface Pear : Fruit
     92 
     93 @end
     94 
     95 #import "Pear.h"
     96 
     97 @implementation Pear
     98 
     99 -(void)show
    100 {
    101     NSLog(@"I'm pear");
    102 }
    103 
    104 @end
    105 
    106 #import <Foundation/Foundation.h>
    107 #import "FruitFactory.h"
    108 
    109 int main(int argc, const char * argv[]) {
    110     @autoreleasepool {
    111         Fruit *fruit = [FruitFactory createFruitByName:@"Apple"];
    112         [fruit show];
    113         Fruit *fruit1 = [FruitFactory createFruitByName:@"Banana"];
    114         [fruit1 show];
    115         Fruit *fruit2 = [FruitFactory createFruitByName:@"Pear"];
    116         [fruit2 show];
    117     }
    118     return 0;
    119 }
  • 相关阅读:
    windows下的文件遍历(使用CFindFile)
    hdu 1728 搜索求最少的转向次数
    linux中vsftpd配置文件详解
    QLineEdit 自动完成(使用setCompleter,内含一个ListView)
    Qt 的内部进程通信机制
    qt 获取windows 的消息(通过MFC的DLL的透明窗体转发消息)good
    JS的类型比较与转换图
    使用C#开发ActiveX控件
    MapXtreme+Asp.net 动态轨迹
    MS SQL 日常维护管理常用脚本(二)
  • 原文地址:https://www.cnblogs.com/oc-bowen/p/5063807.html
Copyright © 2020-2023  润新知