OC基础知识点

来源:互联网 发布:软件研发成果报告 编辑:程序博客网 时间:2024/06/05 12:42

OC基础知识点

 

补充:

1、所有可变的集合才能添加元素(不可变数组能添加元素)

2、id类型就是对象

3、方法需要传递多个参数时,参数以冒号分隔

4、        逗号运算符:优先级最低,低于赋值运算符,计算时,执行最后一个表达式的值

 

 

                                      

sson1   类之间的方法调用

知识点1

@public声明成员变量,此时成员变量属性为公共性,

知识点2

成员声明方式最好采用:NSString *_name,为后期使用养成好习惯

知识点3

类方法: +(返回类型)方法名:(变量类型)变量名   对象方法: —(返回类型)方法名:(变量类型)变量名  

知识点4

为成员变量赋值与使用方法:类名->成员变量


 

                                      

Lesson2   可见度与方法

知识点1

除了@public声明成员变量,在编程过程中一般不使用公开类型,成员变量默认类型为Protect在本类中可以选用private,仅供自己调用

知识点2

为成员变量设置get方法与set方法 //- (void)setName:(NSString *)name;   - (NSString *)getName; 

多参数声明方法:- (void)setName:(NSString *)name Sex:(NSString *)sex Age:(NSInteger)age;

知识点3

@class+ 类名;完成类的声明,成员变量可以设置成类名+成员名 ,方便完成类与类之间的方法调用

知识点4

初始化方法:- (id)initWithName:(NSString*)name Sex:(NSString*)sex Age:(NSInteger)age;

 

                                                   

Lesson3   继承初始化

 

 

继承的五个特点

         1、子类继承父类的实例变量与方法

         2、继承具有单向性(父类不能有子类特征和行为)

         3、oc里没有多继承(能间接继承多个父类)

         4、继承具有传递性

         5、如果子类不满意父类的方法,可以进行重写父类方法(不需要声明)

@class#include#import的区别

#include 的引入头文件是通过copy完成,#import的引入头文件也是通过copy完成,但是能解决重复引入问题,

@class能解决import循环引入的问题  #include <>格式:引用标准库头文件(系统文件),编译器从标准库目录开始搜索, #incluce ""格式:引用非标准库的头文件,编译器从用户的工作目录开始搜索,如果文件名用一对引号括起来则表明该文件是用户提供的头文件,

知识点1:初始化方法实现

#pragma mark 初始化方法1 (指定初始化方法)   //通常把初始化方法中参数最全的作为指定初始化方法

- (id)initWithName:(NSString*)name andAge:(NSString*)age andSex:(NSString*)sex

{

    self = [super init];   //调用父类的方法用super

    if(self)  //判断父类(ISA指针)是否初始化成功,如果不成功子类就不用初始化了

    {  _name = name;_  sex = sex;_  age = age;    }    return self;

}

知识点2:初始化方法2

#pragma mark 初始化方法2  (初始值为name,sex)

- (id)initWithName:(NSString*)name  andSex:(NSString*)sex

{    self = [self initWithName:name andAge:nil andSex:sex];   //调用本类的方法用self

    return self;    }

知识点3:

重写类的description方法

- (NSString*)description    //NSObject的方法,此处为重写

{    return [NSString stringWithFormat:@"name = %@ ,sex =%@,age = %@",_name,_sex,_age];     }

知识点4:便利构造器1

+ (id)personWithName:(NSString*)name andSex:(NSString*)sex andAge:(NSString*)age    (person为小写的类名)

{

    Person *person = [[Person alloc] initWithName:name andAge:age andSex:sex];

    return person;   //之所以能返回指针是因为指针存放在堆中(alloc),存放在栈中的东西是不能返回指针的

    //类方法里面绝对不能使用实例对象     }

#pragma mark 便利构造器2

+ (id)personWithName:(NSString*)name

{    Person *person = [[Person alloc] initWithName:name andAge:nil andSex:nil];

return person;   //之所以能返回指针是因为指针存放在堆中(alloc),存放在栈中的东西是不能返回指针的 }

 

 


 


OcLesson4  Foundation

知识点1:

 

 

NSString

第一部分: 创建字符串 

//第一种方法:不可变的字符串,也是最简单的

NSString *str1 = @"I love you";  //NSString 是苹果创建好的类

//第2种方法:(很重要,可以带多个参数)

NSString *str2 = [[NSString alloc]initWithFormat:@"%@,%@",@"aaa",@"bbbb"];

//第3种方法: 不常用的,麻烦

NSString *str3= [[NSString alloc] initWithString:str1];

//第四种方法:这种方法不常见,没有赋值 // NSString *str4  = [NSString new];

/*****************   类方法创建字符串     *******************/

//   NSString *str5 = [NSString stringWithFormat:@"Anrai"];

    NSString *str5 = [NSString stringWithFormat:@"%@,%@",@"nihao",@" dou"];

//指针重指向

    //    str6 = [str6 capitalizedString];  // 1、更改首字母为大写

    //    str6 = [str6 uppercaseString];    //2、字符串全大写

//    str6 = [str6 lowercaseString];  //3、字符串全小写

//4、获取固定的字串

    NSRange range = NSMakeRange(6, 3);//第一个数字是位置,第二个是长度

    NSString *sub = [str6 substringWithRange:range];

    //5、获取首尾的字串

    NSString *sub_tou = [str6 substringToIndex:5];  //获取头部子串

    NSString *sub_wei = [str6 substringFromIndex:10];//获取尾部子串

//6、字符串拼接

 NSString *appendString = [sub_tou stringByAppendingString:sub_wei];

 //7、插入字符串(替换字符串)

    NSRange range1 = NSMakeRange(0, 0);

NSString *insertString = [str6 stringByReplacingCharactersInRange:range1withString:@"Say "];

//8、求字符串长度

NSUInteger len = [str6 length];

//9、字符串基本类型的转化,要求转化的字符串只能为数字串和“.”

 NSString *numberString = @"3941898.5";

   float number = [numberString floatValue];  // 方法名 :[str xxValue ];

    //10、获取单个字符

unichar ch = [str6 characterAtIndex:3];  //获取从坐标0开始

//11、获取子字符串在字符串中的位置与长度

    NSString *str7 = @"shi";

    NSRange range2 = [str6 rangeOfString:str7];  //子字符串在后面,原字符串在前

    NSLog(@"%@",NSStringFromRange(range2));

//12、替换字符串

    NSString *opeString = @"beijing150516";    //15替换为14

    opeString = [opeString stringByReplacingOccurrencesOfString:@"15"withString:@"14"];  //前旧后新,不可变字符串返回值为指针类型,需要接受后才能输出

//13、删除字符串(不可变字符串没有直接删除的方法,需要执行替换操作实现

    NSString * removeString = [opeString stringByReplacingOccurrencesOfString:@"beijing" withString:@""];

//14、根据文件去创建字符串

  NSString * contentString = [[NSString alloc]initWithContentsOfFile:@"/Users/lanou3g/Desktop/page.txt" encoding:NSUTF8StringEncoding error:nil];

//15、汉字转化为拼音

NSString *str = @"sir, 我 是 li ming";

NSString *pinyin = [ChineseToPinyin pinyinFromChiniseString:str];

NSLog(@"转化 :%@",pinyin); //大写形式

NSArray *array1 = [pinyin componentsSeparatedByString:@" "];//通过空格分隔字符串

    NSLog(@"数组转化 :%@",array1);   

NSString *ss_last = [pinyin substringFromIndex:4];//从第几个位子开始取剩余的字母

NSString *ss_before = [pinyin substringToIndex:1];//取首字母

//16、字符串写入到文件,与导出文件

   /******   字符串的导出   **********/

   NSString *str4 = @"asdfasdfasd发个还是";

NSString *path11 = @"/Users/lanou3g/Desktop/222.txt";

NSError *error2;

 [str4 writeToFile:path11 atomically:YES encoding:NSUTF8StringEncodingerror:&error2];  //字符串写入到文件中

if(error2)

{

 NSLog(@"chucuo %@",[error2 localizedDescription]); //会返回主要的错误信息

}

else

{

NSString *arr = [ NSString stringWithContentsOfFile:path11encoding:NSUTF8StringEncodingerror:nil]; //字符串读取

NSLog(@"-path11-----arr:%@",arr);

NSLog(@"success");

}

//字符串遍历

/*********   数组的遍历有四种方法: for ---  for in  ----  block ---迭代器(  NSEnumerator)     *************/

NSArray *array3 = [NSArray arrayWithObjects:@"11",@"22",@"33", nil];

NSEnumerator *enumerator = [array3 objectEnumerator];  //获取迭代器

NSEnumerator *enumerator1 = [array3 reverseObjectEnumerator];  //获取反序的迭代器,从尾部开始遍历

id obj = nil;

while (obj = [enumerator nextObject]) {    NSLog(@"%@",obj);   }   //正序遍历

while (obj = [enumerator1 nextObject]) {    NSLog(@"%@",obj);   }  //反序遍历

知识点2:NSMutableString

    NSMutableString *mutableString1 = [[NSMutableString alloc]initWithFormat:@"%@%@",@"ni",@"hao"];

    NSLog(@"可变字符串:%@",mutableString1);

    //1、可变的字符串,对于他的修改,实质就是对于自身的修改

    //可变字符串的操作方法 1、拼接

    [mutableString1 appendString:@"Love"];

    NSLog(@"拼接:%@",mutableString1);

    //2、子字符串替换

    // NSRange range3 = NSMakeRange(0, [mutableString1 length]); //第三个参数搜索的方式,第四个参数:搜索的范围

    // [mutableString1 replaceOccurrencesOfString:@"Love" withString:@"Sir" options:NSCaseInsensitiveSearch range:range3];

    [mutableString1 replaceCharactersInRange:NSMakeRange(5, 4)withString:@" Sir"];//整个字符串替换

    NSLog(@"可变字符串替换%@",mutableString1);

知识点3:

 

NSArray

 

 

        /****************************

         第三个内容

         NSArray(数组)的特点:1、可以存放不同类型的数据

         2oc中的数组,其数据必须是对象

         3oc中数组能直接参加运算

         4、数组是有序的

         *************************************/

        Person *person1 = [[Person alloc] initWithName:@"zhangsan"];

        Person *person2 = [[Person alloc] initWithName:@"lisi"];

        //四种方法去创建

        NSArray *array11 =@[person1,person2,@"lisi电视剧"];//语法糖

        NSArray *array12 = [[NSArray alloc]initWithObjects:person1,person2,nil]; //使用alloc init方法去创建

        NSArray *array13 = [NSArrayarrayWithObjects:person1,person2,nil];   //类方法

        NSArray *array14 = [[NSArray alloc]initWithArray:array1];//根据数组创建另一个数组

        //打印数组的三种方式

        NSLog(@"%@",array1);//第一种:打印汉字时不能正常显示

        for(int i =0; i < 3; i++)

        {

            NSLog(@"%@",array1[i]);//语法糖,第二种打印方式

        }

        //第三种打印oc中的循环遍历

        for (id objectin array1)

        {

            NSLog(@"%@",object);

        }

        for (Person *objectin array12)

        {

            NSLog(@"%@",object);

        }

        //创作数组的方法

        //1、求数组里面元素的个数

        NSUInteger array3count = [array3count];

        NSLog(@"数组1的元素个数:%lu",array3count);

        //2、删除元素 ---(不可变数组没有删除元素的方法)

        //3、添加元素

        array3 =  [array3 arrayByAddingObject:@"liuhui"];

        //第三种打印oc中的循环遍历

        for (id objectin array3)

        {

            NSLog(@"%@",object);

        }

        //4、获取数组里面第一个元素

        Person *temp = [array1 firstObject];

        NSLog(@"第一个元素%@",temp);

        //5、获取数组里面最后一个元素

        NSString *string = [array1 lastObject];

        NSLog(@"最后一个元素%@",string);

        //6、判断数组里面是否包含某个元素

        BOOL result = [array1containsObject:person2];  //6、判断数组里面是否包含某个元素

        NSLog(@"%d",result); //%g 打印有效位数

        //7、判断一个元素到底在哪一个位置

        NSUInteger index = [array1indexOfObject:person2];//坐标位置

        NSLog(@"%lu",index);

知识点4:

NSMutableArray

 

  /*第四个内容 NSMutableArray     ****************/

        NSMutableArray *mutableArray = [[NSMutableArray alloc] init];

        [mutableArray addObject:person1];

        [mutableArray addObject:person2];

        NSLog(@"mutableArray个数:%lu",[mutableArraycount]);

        //删除元素

        Person *person3 = [[Person alloc]initWithName:@"huang"];

        [mutableArray addObject:person3];

        //       NSArray *array = @[person2,person3];

        //       [mutableArrayremoveObjectsInArray:array];//批量删除

        //       [mutableArrayremoveAllObjects];//全部删除

        //       [mutableArray removeLastObject];//删除最后一个元素

        //       [mutableArrayexchangeObjectAtIndex:0withObjectAtIndex:2];//交换两个元素

        NSArray *arr1 = @[person1];  NSArray *arr2 =@[person2];  NSArray *arr3 =@[person3];

        NSArray *arr = @[arr1,arr2,arr3];

        for (id objectin arr) {

            NSLog(@"%@",object);

        }

知识点5:

 

NSNumber

是更具体的包装类,主要方法有三种:

+ numberWithXxx

 

-initWithXxx类型封装

 

- xxxValue 格式转换

 

 

  /***      第五个内容 NSNumber   *************/

        //NSNumber ,封装基本类型,使其变为对象类型

        NSNumber *number1 = [[NSNumber alloc]initWithInt:2];

        NSArray *arr4 = @[number1];

        NSNumber *resultNumber = arr4[0];

        int result1 = [resultNumberintValue];

        NSLog(@"result = %d",result1);

        //第二种方法实现

        NSArray *arr5 = @[@(1),@(2),@(3)]; //语法糖

        int result2[3];

        for (int i =0; i < 3; i++) {

            NSNumber *resultNumber = arr5[i];

            result2[i] = [resultNumber intValue];

            NSLog(@"result%d =%d",i,result2[i]);

        }

知识点6:

NSValueNSNumber的父类

 

/***  第六个内容 :  NSValue   *******/

        NSRange range11 = NSMakeRange(2,5);

        NSValue *value = [NSValue valueWithRange:range11];//便利构造器

知识点7:

查阅API文档

1Window->Documentation and API->select

  (2)Alt + 关键字 " " + reference

  (3)编程界面中右边框中有Quick Help ,鼠标移动到关键字上即可查询

 more related详细:继承的父类、遵守的协议、框架framework、适用环境、声明地点、

 (!!!!后两个较为重要)  相关的文档中会有解释、示例代码(sample code

 

知识点8:NSDictionary

NSDictionary (字典:包含键(key)与值(value)且一一对应)特点:

     1)只能存对象

     2)字典是无序的

     3key值是不可以重复的,如果重复程序会自动保留第一对键值对 ---(对可变字典不成立)

     4value值可以重复

     5key值与value值必须是对象

6)一般情况key值使用字符串

    NSDictionary *dict = [[NSDictionary alloc]initWithObjectsAndKeys:@"hao",@"111",@"ren",@"222",nil];//输出顺序key值在前

    NSDictionary *dict1 =[NSDictionarydictionaryWithObjectsAndKeys:@"123",@"1",@"456",@"4",nil];

    NSDictionary *dict2 = [NSDictionarydictionaryWithObject:@"value1"forKey:@"key1"];//不常用

    NSDictionary *dict3 =@{@"a3":@"value3",@"z1":@"value1",@"k2":@"value1"}; //重点

    NSLog(@"111%@",dict);

    NSLog(@"222%@",dict1);

    NSLog(@"333%@",dict2);

    NSLog(@"444%@",dict3); //字典是无序的

    NSInteger dictCount = [dict3 count];//1、字典的键值对计数方法

    NSLog(@"计数%lu",dictCount);

    NSArray *keys = [dict3 allKeys];//2、拿出字典所有的key

    NSLog(@"dict3中的key值:%@",keys);

    NSArray *values = [dict3 allValues];//3、拿出字典中所有的value

    NSLog(@"dict3中的value值:%@",values);

    Person *person1 = [[Person alloc] initWithName:@"zhangsan"];

    Person *person2 = [[Person alloc] initWithName:@"lisi"];

    NSDictionary *finalDic = @{@"key1":person1,@"key2":person2};//存放对象

    NSLog(@"%@",finalDic); 

    [dict3 objectForKey:@"k2"];// 4、拿出某一个value,字典的方法---objectForKey

    NSString *value = dict3[@"k2"];//语法糖实现

    NSLog(@"拿出某一个value值:%@",value);

    //根据value拿出某些个key

    NSArray *keys2 = [dict3 allKeysForObject:@"value1"];

    NSLog(@"根据value拿出某些个key%@",keys2);

    //6、遍历字典--value

    for (id objectin dict3) {

        NSLog(@"遍历字典%@",dict3[object]);

    //局限性

    /************** 第二种遍历方式  *************/

    NSArray *keyArray = [dict3 allKeys];

    for (NSString *keyin keyArray) {   NSLog(@"%@",dict3[key]);  }

字典的其他使用 1、数组与字典可以相互嵌套

     2、如果字典里面去放数组,一般情况把数组作为value

知识点9:

 

 NSMutableDictionary 可变数组

    //       NSMutableDictionary *mutableDic = [[NSMutableDictionary alloc]initWithCapacity:10];//一次性开辟10个空间

    NSMutableDictionary *mutableDic1 = [NSMutableDictionary dictionary];//继承不可变字典

    [mutableDic1 setObject:person1 forKey:@"key3"];//1、往可变的字典里面添加元素

    [mutableDic1 setObject:person2 forKey:@"key4"];

    [mutableDic1 setObject:person2 forKey:@"key3"];

    NSLog(@"mutableDic1键值对个数:%lu",[mutableDic1 count]);

    NSLog(@"%@",mutableDic1); //如果可变字典key值重复,则会保留最后一个key值对应的键值对

    //2、删除字典里面的元素

    //       [mutableDic1 removeAllObjects];//删除字典里所有元素

    //       NSLog(@"删除全部:%@",mutableDic1);

    //删除某个值

    //       [mutableDic1 removeObjectForKey:@"key3"];

    //       NSLog(@"删除某个值:%@",mutableDic1);

    NSArray *delectArray =@[@"key3",@"key4"];

    [mutableDic1 removeObjectsForKeys:delectArray];

    NSLog(@"删除值:%@",mutableDic1);

知识点 10 :

NSSet

 

NSset可以存放任何数据类型的对象,不是数据,它是无序的集合内不能存不同类型的对象

NSSet *set = [NSSet setWithObjects:@"you",@"are",@"boy",nil];

    NSLog(@"%@",set);

    //把数组中的元素放到set中(以下三行代码去除重复元素)

    NSArray *arraySet =@[@"1",@"2",@"1"];

    NSSet *set1 = [NSSet setWithArray:arraySet];

    //操作set方法

    NSLog(@"set元素个数:%lu",set1.count);//统计set中元素的个数

    NSLog(@"set所有元素:%@",set1.allObjects);//取出集合中所有元素

    NSLog(@"set某个元素:%@",[set1 anyObject]);//取出集合中某个元素,不保证随机性

    NSLog(@"%d", [set1 intersectsSet:set]);//取交集,返回值BOOL类型

知识点 11 :

NSMutableSet

    NSMutableSet *set2 = [NSMutableSet setWithObjects:@"1",@"2",@"3",nil];

    NSMutableSet *set3 = [NSMutableSet setWithObjects:@"4",@"2",@"3",nil];

    NSLog(@"%d", [set2intersectsSet:set3]);//取交集,返回值BOOL类型

    [set2 unionSet:set3];//取并集,返回值void类型

    [set2 minusSet:set3];//取差集,返回值void类型

[set2 removeAllObjects];//删除集合所有元素

知识点 11 :

NSCountedSet

  NSCountedSet *countSet = [NSCountedSetsetWithObjects:@"5",@"3",@"6",@"3",nil]; //输出对应元素的个数

    NSLog(@"%@",countSet);


 


Lesson6 protocol(协议只是一个头文件,分为正式与非正式两种)

正式协议:

 

 

遵守协议的才是代理

这种协议为正式协议注意:oc中虽然没有多继承,但是一个类能遵守多个协议,这样间接的实现了多继承

  

@protocol MarryProtocol <NSObject>

@required  //默认是@required必须实现的

#pragma mark 协议一:赚钱

- (void)makeMoney;

@optional  //可以选择性实现

- (void)lookAfterBady;

@end

@interface Boy : NSObject<MarryProtocol> //遵守协议

@interface Girl :NSObject

{   NSString *_name;     id<MarryProtocol>_delegate;//代理声明的变量  }

 #pragma mark setter方法(给代理赋值)

-(void)setDelegate:(id<MarryProtocol>)delegate;

- [girl setDelegate:boy];//女孩把男孩作为自己的代理

非正式协议

//非正式协议,在别的类中声明

@protocol informalityProtocol <NSObject>

- (void)makeMoney1;

@end

@interface Person :NSObject

@end


使用数组完成通讯录的制作

 

 

 

过程

1、//定义一个可变的数组,存放联系人

    NSMutableArray *contactArray = [NSMutableArrayarray]; //最外层通讯录数组

2//大数组放26个小数组

        for(int i =0; i< 26; i++) //第二层 26个数组的创建

        NSMutableArray *array1 = [NSMutableArrayarray];

            [contactArray addObject:array1];   }

 3//添加联系人   NSMutableArray *groupArray0 = [contactArrayobjectAtIndex:0];//1、拿到对应的分组

                    [groupArray0  addObject: p0];//2、往对应分组添加联系人

4//9、展示通讯录中所有联系人

        for (NSMutableArray *arrayin contactArray) {

            for (Person *personin array) { NSLog(@"%@",person); }   }

5、按照条件显示联系人信息

        for (NSMutableArray *arrayin contactArray) {

for (Person *personin array) {

if ([[person3 getGroupName] isEqualToString:@"a"]) //获得a组的所有联系人信息

if ([[person4 getPhoneNumber] isEqualToString:@"1686891"]) 4、根据电话号码搜索联系

if ([[person2 getSex] isEqualToString:@""])//5、获取所有女性联系⼈

                NSLog(@"%@",person);

            }

        }

       //6、根据姓名删除联系⼈(for-in循环里不能直接删除,否则可能会引起崩溃)

        NSMutableArray *opeArray;

        NSMutableArray *delectNameArray = [NSMutableArrayarray] ;

        for (NSMutableArray *array3in contactArray)

        {

            for (Person *person3in array3) {

               

                if ([[person3getName]isEqualToString:@"赵信z"]) {

                    opeArray = array3;

                    [delectNameArrayaddObject:person3];

                    //  [array3 removeObject:person3];  //(for-in循环里不能直接删除,否则可能会引起崩溃)

                }

            }

        }

        //统一删除

        [opeArray removeObjectsInArray:delectNameArray];

////        7、删除某个分组全部联系⼈

        NSMutableArray *delectArray = contactArray[25];

        [delectArray removeObject:p5];   //删除Z组中的某个联系人

       [delectArray removeAllObjects]; //删除Z组中的所有联系人


 

 

使用字典完成通讯录的制作

 

 

 

 

通讯录

初始化方法

#pragma mark 通讯录初始化方法

- (id)initWithContactName:(NSString*)name

{

    self = [superinit];

    if(self)

    {

        _contactName = name;

        _contactDic = [NSMutableDictionarydictionary ];//对通讯录进行初始化

    }

    returnself;

}

 

创建通讯录管理类

ContactManager *manager = [[ContactManageralloc]initWithContactName:@"mac通讯录"];

//往通讯录里存储联系人

 [manager addContactWithPerson:p0];

 

 

 

获取姓名首字母

#pragma mark 获取姓名首字母

- (NSString*)getFirstAlbumOfName:(NSString*)name

{

    NSString *pinyin = [ChineseToPinyinpinyinFromChiniseString:name];

    NSString *name_tou = [pinyinsubstringToIndex:1]; //获取姓名首字母,默认大写的

    //   NSLog(@"%@",[group lowercaseString]);  //3、字符串全小写

    return name_tou;

}

 

 

 

添加联系人的方法

#pragma mark 添加联系人的方法

- (BOOL)addContactWithPerson:(Person*)person

{

    if ([persongetName].length <1 || [persongetName] == nil || [[persongetName]isKindOfClass:[NSNullclass]]) { returnNO;  }

    //首先判断通讯录里面有没有对应的分组

    NSString *group = [selfgetFirstAlbumOfName:[persongetName]];//获取姓名首字母

    NSArray *keyArray = [_contactDicallKeys];    //拿到字典里面所有的key值,即为分组的名字

    //判断所有分组的数组是否包含此联系人应该在的分组

    if ([keyArraycontainsObject:group]) {

        //包含的情况

        NSMutableArray *valueArray = [_contactDicobjectForKey:group]; //根据key找到对应的value数组

        [valueArray addObject:person];

        returnYES;

    }

    else

    {//不包含的情况

        NSMutableArray *valueArray = [NSMutableArrayarray]; //没有对应的数组就需要创建

        //先把联系人放到这个数组

        [valueArray addObject:person];

        //把数组放到字典中

        [_contactDicsetObject:valueArrayforKey:group];

            returnYES;

    }

    returnNO;

}

 

 

展示所有联系人

  NSArray *keysArray = [_contactDicallKeys];//拿出所有分组名

    keysArray = [keysArray sortedArrayUsingSelector:@selector(compare:)];    //a-z排序,compare是选择器

    //遍历分组名数组

    for (NSString *keyin keysArray) {

        NSMutableArray *valueArray = [_contactDicobjectForKey:key]; //拿出分组名对应的信息

        NSLog(@"----%@-----",key);

        for (Person *pin valueArray) { NSLog(@"%@",p);  }

    }

 

 

 

 

删除联系人

- (BOOL)deleteContactWithPerson:(Person*)person

{

    NSString *group = [selfgetFirstAlbumOfName:[persongetName]];

    NSMutableArray *array = [_contactDicobjectForKey:group];

    [array removeObject:person];  //先删除这个联系人

    if(array.count <1)//如果分组里面没有其他联系人的时候,把整个分组删除掉

    {    [_contactDicremoveObjectForKey:group];   }

       returnYES;

}

 

 

 

按照性别搜索全部的女性联系人

- (void)searchContactBySex:(NSString*)sex

{    NSArray *keysArray = [_contactDicallKeys];

    for (NSString *keyin keysArray) {

        NSMutableArray *array =_contactDic[key];//语法糖

        for (Person *pin array) {

            if ([[pgetSex]isEqualToString:sex]) {  NSLog(@"%@",p);  }

      }  }

}

 

按照号码

搜索全部的联系人

- (void)searchContactByPhoneNumber:(NSString*)phoneNumber

{

    NSArray *keysArray = [_contactDicallKeys];

    for (NSString *keyin keysArray) {

        NSMutableArray *array =_contactDic[key];//语法糖

        for (Person *pin array) {

            if ([[pgetPhoneNumber]isEqualToString:phoneNumber]) {

                NSLog(@"%@",p);

            }

        }

    }

}

 

 

 

 


 

 

Lesson7   Block

纠正知识点1

int array[10];的类型是int[10],函数是array——>结论:函数类型有无数个

纠正知识点2

 aa()  //默认返回为整形类型

 

 

block之局部变量

 

// 内存分类 :堆区(存指针) 栈区(系统自己管理)  常量区:程序结束后释放  静态区(全局区)代码区,

全局变量和静态变量的存储是放在一块的,初始化的全局变量和静态变量在一块区域,未初始化的全局变量和未初始化的静态变量在相邻的另一块区域。程序结束释放。 

//block里面局部变量的使用,block中引用局部变量是一个拷贝过程,拷贝之后变为一个常量,此时block的存储区域为栈区

代码代码区存放函数体的二进制代码
int a = 0; //全局初始化区 
char *p1; //全局未初始化区 
main() 

 int b; // 
  char s[] = "abc"; // 
 
char *p2; // 
  char *p3 = "123456"; //123456\0在常量区,p3在栈上。 
  static int c = 0 //全局(静态)初始化区 
  p1 = (char *)malloc(10); 
  p2 = (char *)malloc(20); 
//分配得来得10和20字节的区域就在堆区。 
strcpy(p1, "123456"); 
//123456\0放在常量区,编译器可能会将它与p3所指向的"123456"优化成一块。 

 

block之全局变量

 

  __block int number = 10;  //__block 作用声明定义的变量在block中作为常量被使用,

(如果在block中要修改局部变量,这需要使用__block声明定义的局部变量)

    void (^myBlock)(int x) = ^void(int x) //右边的返回类型不能丢

 

block之实现

//3block的实现部分,返回值最好加上实现部分的返回值类型

 NSInteger (^block)(NSInteger x, NSInteger y) = ^NSInteger( NSInteger x, NSInteger y)

 NSArray *(^aBlock)(NSString * str,NSString *str2);NSString *(^aBlock)(NSString * str,NSString *str2);

 实现:aBlock = ^( NSString * str,NSString *str2){ return str1;  }

 调用:aBlock(@"string1" @"string2");

 

 

 

 

 

block之排序

(练习compare

的使用方法,不可变数组使用)

 

personArray = [personArray sortedArrayUsingComparator:^NSComparisonResult(id obj1, id obj2)

{

    //下面不是强制类型转换,相当于类型声明

   //不可变数组使用 sortedArrayUsingComparator:^NSComparisonResult(id obj1, id obj2)

        Person *personObj1 = (Person*)obj1;

        Person *personObj2 = (Person*)obj2;

        if([[personObj1 getName] compare:[personObj2 getName]] > 0){

            NSLog(@"%ld",(long)NSOrderedDescending);

            return NSOrderedDescending; // +1

        }else if([[personObj1 getName] compare:[personObj2 getName]] < 0){

           // NSLog(@"%ld",(long)NSOrderedAscending);

            return NSOrderedAscending;  // -1

        }else{

            NSLog(@"%ld",(long)NSOrderedSame);

            return NSOrderedSame;    // 0

        }

 } ];

block之排序

(练习compare

的使用方法,可变数组使用)

 

NSMutableArray *personMutableArray = [NSMutableArray arrayWithObjects:p1,p2,p3,p4, nil];

[personMutableArray sortUsingComparator:^NSComparisonResult(id obj1, id obj2) {

//下面不是强制类型转换,相当于类型声明

//可变数组使用 sortUsingComparator:^NSComparisonResult(id obj1, id obj2)

 Person *personObj1 = (Person*)obj1;     Person *personObj2 = (Person*)obj2;

Compare 的使用

 

主要适用于字符串与数字的比较       链接:http://zcw-java.iteye.com/blog/1886817 

 NSCaseInsensitiveSearch  忽略大小写的比较字符串 

NSNumericSearch       比较字符串的个数 

NSLiteralSearch       区分大小写,进行完全比较

内存

最大的栈空间为 1M 内存的%80都被分为堆区

 

 


 

                                          

Lesson8_Category

 

 

 

 

 

 

 

知识点1:

 

宏定义

比较大小

 

 

#define  MAXValue1(A,B)  A > B ? A : B //第一版本 3>2?3:2>5? 3>2?3:2:5

#define  MAXValue2(A,B) (A) > (B) ? (A) : (B)//第二版本

#define  MAXValue3(A,B) ((A) > (B) ? (A) : (B))//第三版本

#define  MAXValue4(A,B) ({int __a = (A);int __b = (B); __a > __b ? __a : __b;})//第四版本

#define  MAXValue5(A,B) ({__typeof(A)__a = (A);__typeof(B)__b = (B); __a > __b ? __a : __b;})//第五版本,不受类型限制

  int result1 =MAXValue1(3 >2 ? 3 :2,5);   //第一个版本:套用三目运算符词性检测  NSLog(@"result1 = %i",result1);

        // 第二个版本的问题

        int result2 =2 *MAXValue2(3,5);

        NSLog(@"result2 = %i",result2); //在没有大括号的时候,外围的运算会提前加入,导致运算出错

        //第三个版本的问题

        int a =11, b =10;

        int result3 =MAXValue3(a++, b);

        NSLog(@"result3 = %i",result3); //如果++参与两次运算 则会出现错误

        //第四个版本的问题,针对整形类型

        int aa =6, bb =10;

        int result4 =MAXValue4(aa++, bb);

        NSLog(@"result4 = %i",result4);

        //第五个版本的问题,广泛版本

        float c =6, d =10;

        float result5 =MAXValue5(c++, d);

        NSLog(@"result5 = %f",result5);

 

 

 

 

Category

知识点

 

 

Category (类目、类别、分类)主要用来给没有源代码的类添加方法

如果Category里面写了跟原始类同名的方法,若是实例方法(-),则外面使用的时候是原始类的方法,如果这个方法是类方法(+),则外面使用的是category的方法类目:给原始类添加方法,子类可以继承这个方法

类目:为已知的类增加新的方法;延展:通知在本类的定义里使用类目来声明私有方法;协议:协议声明了可以被任何类实现的方法。
注意:这些手段只能增加类的方法,并不能用于增加实例变量,要增加类的实例变量,只能通过定义子类来间接实现。

1)声明类目
@interface NSString (NumberConvenience)
-(NSNumber *)lengthAsNumber;
@end

局限性1:无法向类中添加新的实例变量。类别没有位置容纳实例变量。

局限性2:名称冲突,即类别中得方法与现有的方法重名。当发生名称冲突时,类别具有更高的优先级。你的类别方法将完全取代初始方法,从而无法再使用初始方法。有些编程人员在自己的类别方法中增加一个前缀,以确保不发生名称冲突。

3)类目的作用:cocoa中得类别主要用于3个目的:

第一,将类的实现分散到不同文件或者不同框架中。第二,创建对私有方法的前向引用。第三,向对象添加非正式协议

 

 

延展:extension

延展:extension 类名+()作用:管理私有变量和私有方法  OC中没有真正的私有变量和私有方法

@interfaceTeacher()

- (void)showMypay; //只能够自己使用

@propertyNSString *pay; //私有类型

@end

- (void)printPay

 Teacher *tea = [[Teacheralloc]init];   tea.pay = @"200";

[tea showMypay]; //只能由展延类的对象个人使用,不能超出本.m文件

}


 

 

Lesson10_delegate_block

 





非正式协议   

@protocol boyDelegate<NSObject>  //非正式协议

- (void)washClothes;

@end

 

@interface Boy : NSObject

@(nonatomic,assign)id<boyDelegate>delegate; //retain会造成循环引用代理要用assign

- (void)clothesDirty;

- (void)setDelegate:(id<boyDelegate>)delegate;

 

@end

 

 

 

Block 方法的使用

typedef void(^MYBLOCK)(void);

//@class Boy;

@interface Girl : NSObject  //<boyDelegate>

@property (nonatomic,retain)Boy *boyFriend;

@property (nonatomic,copy)MYBLOCK block;  //只写一个block是在栈区,用copy后就放到堆区了

- (void)test;

@end

 

 

 


 


Lesson9_Memory

 

 

 

内存方法

谨记

oc 中的内存方法:MRCMannul Reference Counting,手动引用计数管理,automatic reference counting(ARC,自动引用计数管理),garbage collection(垃圾回收机制)

   iOS中内存方法: ARCXcode会帮助管理内存 

    MRC:需要开发人员手动去控制应用计数,一块内存区域引用计数一旦变为0,系统会自动将其删除。ios里面的关键字有 alloc retainreleaseautoreleasecopy,其中alloc的作用开辟内存引用从0变为1retain的作用引用计数进行加1操作,release的作用多内存引用计数立刻进行减1操作,autorelease是对内存引用计数在未来的某个时间进行减1操作。copy的作用是把原来内存的内容(或是一个对象)拷贝到新的内存区域,原来内存区域的引用计数不变,新的区域引用计数由0变为1

Java 中的内存管理为:garbage collection (垃圾回收机制)

 

 NSString *name = [[NSString alloc]initWithString:@"haha"];  //确定只有一个字符串后会存储在常量

NSString *name2 = @"haha";   //确定只有一个字符串后会存储在常量区

NSString *name3 = [[NSString alloc]initWithFormat:@"%@ %@ %@",@"aa",@"bb",@"cc"];//此时字符串个数不确定,然后会存储在堆区

        //不是所有的对象都能使用copy,只有遵守了NSCopying协议的对象才能使用copy


黄金原则

// MRC管理内存一条原则:有加1就要有减1,有谁开辟就有谁来释放,谁加1谁就减1

 assign :基本数据类型使用      retain :所有对象类型都能使用

         copy:遵守了copy协议并且实现了协议的才能用,慎重使用,能把字符串从栈区copy到堆区

         代理使用assignblock使用copy,对于NSString一般使用Copy


类的内存分配长度


语法糖也是一种便利构造器

        NSLog(@"%lu",sizeof([Personclass])); //类的长度为8,与C语言中的指针相似

        NSLog(@"%lu",sizeof(p1)); //类的长度为8,与C语言中的指针相似       [p1 release];

//        NSLog(@" test2.name =%@",p1.name);//标记性删除,不一定会崩溃

        // OC的容器类会对里面的对象执行retain操作,在数组里面person对象的计数量加1,当对象被移除的时候会执行减1操作

        NSArray *array = [NSArray arrayWithObjects:person1,person2, nil];//凡是便利构造器不需要release




深拷贝与浅拷贝

的区别与用法

    NSString *name1 = [[NSStringalloc]initWithFormat:@"%@",@"xxx"];//NSString使用copy时是浅拷贝

    NSString *name2 = [name1copy];//这种拷贝没有重新分配空间,是一种浅拷贝,等价于retain,只拷贝指针,深拷贝拷贝的内容

NSString *name3 = [name1mutableCopy]; //此时mutableCopy为深拷贝

 //   NSMutable类型使用copy或者mutableCopy都是深拷贝

NSMutableString *result2 = [mutablestring copy];

//copy 出来的东西都是不可变的,所以不能使用拼接,但此时为深拷贝

        NSMutableArray *array5 = [NSMutableArrayarrayWithObjects:@"name1",@"name2",nil];

        NSMutableArray *array6 = [array5copy]; //此处为深拷贝

        NSMutableArray *array7 = [array5mutableCopy]; //此处为深拷贝






@autoreleasepool

  @autoreleasepool {  //一级 pool 

    @autoreleasepool {  //二级 pool

            [test2 retain];

            @autoreleasepool {  //三级 pool

            [test2 release];

            }

            [test2 retain];

        } }

//出了最近的自动释放池后autorelease就会执行减1操作(因为autoreleasepool内可以套无数个autoreleasepool))

 NSAutoreleasePool *pool = [[NSAutoreleasePool alloc]init];//。。内容。。 [pool release];

这两句相当于       @autoreleasepool { 内容 。。。。}

dealloc

- (void)dealloc

{   [_name release];  //对成员变量进行最后的释放

[super dealloc];  //必有,而且需要放在最下面

}

 

getter方法

- (NSString*)name

{  

     return[[_name retain]autorelease];

 //适用于retaincopy的方法,如果是assign方法,直接返回就行 

 }

 

setter方法

- (void)setName:(NSString *)name

{   if(_name != name)

    {

     [_name release];

     _name = [name copy]; 

    //copy 方法此处使用copyretain方法此处用retainassign方法直接赋值就可

 

 }

 

 

 

 

初始化方法

- (id)initWithName:(NSString*)name withSex:(NSString*)sex withAge:(NSInteger)age

{   self = [superinit];

    if(self) { /****  为了避免内存过度释放,选用self.成员变量,会自动retain/copy +1 *****/

        //第一种

        _name = name;

        _sex = sex;

        _age = age;

  //第二种

        self.name = name;

        self.sex = sex;

        self.age = age;

/***  但是,在子类再次进行初始化的时候会出现父类执行子类的set方法的情况,因此出现下面的写法  ****/

        //第三种

        _name = [namecopy];

        _sex = [sexcopy];

        _age = age; 

    }   returnself;

}

 

 

 

@property

成员变量成名

 

三大属性:

retainassigncopy

 

 

 

 

@property (nonatomic,copy)NSString *name; //NSString一般使用copy方法

@property (nonatomic,copy)NSString *sex;

@property (nonatomic,assign)NSInteger age;

//等价于实现了:成员变量声明,setter方法 getter方法

    设置成员变量的@property属性时,默认为atomic,提供多线程安全。在多线程环境下,原子操作是必要的,否则有可能引起错误的结果。Nonatomic : 禁止多线程,变量保护,提高性能。读写属性方面默认可读可写(readwrite,使用只读属性时需要声明(readonly

Assign:对基础数据类型NSIntegerCGFloat)和C数据类型(int, float, double, char)等等

Retain:对其他NSObject和其子类对参数进行release旧值,再retain新值
  指定retain会在赋值时唤醒传入值的retain消息。此属性只能用于Objective-C对象类型,而不能用于Core Foundation对象。注意:把对象添加到数组中时,引用计数将增加对象的引用次数+1

Copy:对NSString 它指出,在赋值时使用传入值的一份拷贝。拷贝工作由copy方法执行,此属性只对那些实行了NSCopying协议的对象类型有效

retain 是指针拷贝,copy是内容拷贝

ARC1copy只用于NSString\block 2retain适用于:除了NSString\block以外的OC对象 3assign:基本数据类型、枚举、结构体(非OC对象),当2个对象相互引用,一端retain,一端用assign

ARC:(1copy只适用于NSString\block 2strong适用于:除了NSString\block以外的OC对象3weak,当2个对象相互引用,一端strong,一端用weak4assign:基本数据类型、枚举、结构体(非OC对象)

 

 


OcLesson11_NSDate

 

 

NSDate

//如果NSDate只能打印出地0时区的时间,获取当前的时间在实际上开发中很少使用

        NSDate *date = [NSDatedate]; //即使时间

        NSLog(@"%@",date);

        NSDate *date1 = [NSDatedateWithTimeIntervalSince1970:1435235000];//默认时间单位为秒

        NSLog(@"date1 = %@",date1);

 

 

 

 

 

NSTimeInterval

        NSTimeInterval time = [date1timeIntervalSinceDate:date];//计算两个日期的间隔时间,

        NSLog(@"%f",time);

        NSDate *date2 = [NSDatedateWithTimeIntervalSinceNow:70];

        NSTimeInterval time2 = [date2timeIntervalSinceDate:date];

        if (time2 >0 && time2 <60) {

            NSLog(@"发生在%f s",time2);

        } else  if(time2 >60 && time2 <3600){

            NSLog(@"发生在%.0f分钟前",time2/60);

        }else{

         NSLog(@"发生在%.0f小时前",time2/3600);

        }

 

 

 

 

 

 

 

 

 

 

日期和字符串相互转化的辅助类

      //日期和字符串相互转化的辅助类

        NSDateFormatter *formatter = [[NSDateFormatteralloc]init];

        [formatter setDateFormat:@"yyyy-MM-dd HH:mm:ss aa"];

        //先使用系统提供好的系统格式 // NSDateFormatterShortStyle NSDateFormatterLongStyle

//        [formatter setTimeStyle:NSDateFormatterFullStyle];

//        [formatter setDateStyle:NSDateFormatterFullStyle];

        NSString *dateString = [formatterstringFromDate:date]; //辅助类

        NSLog(@"dateString = %@",dateString);

        //把字符串转换为时间

        NSDate *finalDate = [formatterdateFromString:@"2014-06-25 14:49:17"];

        NSLog(@"finalDate = %@",finalDate);

获取当前的Locale的详细时间

        //获取当前的Locale的详细时间

        NSLocale *cn = [NSLocalecurrentLocale];

        NSLog(@"cn = %@",[datedescriptionWithLocale:cn]);

        NSDate *earlier = [date1earlierDate:date2];

        NSDate *later = [date1laterDate:date2];

 

 

 

 

 

           

 

 

 

0 0
原创粉丝点击