ios基础-5-2类间通信广播

广播三要素:

  • 广播中心
  • 发起人
  • 接收者

广播其实就是一种观察者模式,需要注册观察者,被监听事件触发,通知观察者的回调方法

广播可以支持:

  • 1-1
  • 1-n
  • n-n
  • n-1
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
//
// main.m
// 5-2类通信广播
//
// Created by wanggang on 2017/8/2.
// Copyright © 2017年 hackingangle. All rights reserved.
//
#import <Foundation/Foundation.h>
#import "ClassA.h"
#import "ClassB.h"
#import "ClassBB.h"
int main(int argc, const char * argv[]) {
@autoreleasepool {
ClassA *a = [[ClassA alloc] init];
ClassB *b = [[ClassB alloc] init];
ClassBB *bb = [[ClassBB alloc] init];
[a sendNof];
}
return 0;
}
//
// ClassBB.h
// 5-2类通信广播
//
// Created by wanggang on 2017/8/2.
// Copyright © 2017年 hackingangle. All rights reserved.
//
#import <Foundation/Foundation.h>
@interface ClassBB : NSObject
@end
//
// ClassBB.m
// 5-2类通信广播
//
// Created by wanggang on 2017/8/2.
// Copyright © 2017年 hackingangle. All rights reserved.
//
#import "ClassBB.h"
@implementation ClassBB
- (id) init {
self = [super init];
if (self) {
[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(callbackNof:) name:@"USERINFO" object:nil];
}
return self;
}
- (void) callbackNof:(NSNotification*) nof {
NSLog(@"广播回调 ClassBB");
NSLog(@"%@ %@", nof.object, [nof.userInfo objectForKey:@"username"]);
}
@end
//
// ClassA.h
// 5-2类通信广播
//
// Created by wanggang on 2017/8/2.
// Copyright © 2017年 hackingangle. All rights reserved.
//
#import <Foundation/Foundation.h>
@interface ClassA : NSObject
- (void) sendNof;
@end
//
// ClassA.m
// 5-2类通信广播
//
// Created by wanggang on 2017/8/2.
// Copyright © 2017年 hackingangle. All rights reserved.
//
#import "ClassA.h"
@implementation ClassA
- (void) sendNof {
// [[NSNotificationCenter defaultCenter]postNotificationName:@"USERINFO" object:nil userInfo:nil];
NSMutableDictionary *dict = [[NSMutableDictionary alloc] init];
[dict setValue:@"hackingangle" forKey:@"username"];
[[NSNotificationCenter defaultCenter]postNotificationName:@"USERINFO" object:[NSNumber numberWithInteger:5] userInfo:dict];
}
@end
//
// ClassB.h
// 5-2类通信广播
//
// Created by wanggang on 2017/8/2.
// Copyright © 2017年 hackingangle. All rights reserved.
//
#import <Foundation/Foundation.h>
@interface ClassB : NSObject
@end
//
// ClassB.m
// 5-2类通信广播
//
// Created by wanggang on 2017/8/2.
// Copyright © 2017年 hackingangle. All rights reserved.
//
#import "ClassB.h"
@implementation ClassB
- (id) init {
self = [super init];
if (self) {
// 参数1:观察者对象是谁
// 参数2:回调方法是谁,另外selector是什么鬼???
// 参数3:广播名称
// 参数4:广播附带参数
[[NSNotificationCenter defaultCenter]addObserver:self selector:@selector(callbackNofication:) name:@"USERINFO" object:nil];
}
return self;
}
- (void) callbackNofication {
NSLog(@"广播回调");
}
- (void) callbackNofication:(NSNotification*)nof {
NSLog(@"广播回调带参数");
NSLog(@"%@ %@", nof.object, nof.userInfo);
}
// 销毁观察者
- (void) dealloc {
[[NSNotificationCenter defaultCenter]removeObserver:self name:@"USERINFO" object:nil];
}
@end

ios基础-5-1类间通信block

block

  1. block就是一个代码块
  2. block本质上就是一个函数指针,即代码块的内存地址
  3. block常用来传递值,本质就是把block地址传递到调用block地方
  4. block可以访问外部变量,但是不能修改外部变量
  5. 如果一定要修改外部变量,可以在外部变量前面增加修饰词_block
  6. 利用typedef可以定义block类型
    • typedef int (^sum) (int, int)

类通信坑-交叉引用

block极力避免的就是类之间的方法的互相依赖,也就是交叉引用

交叉引用来个定义:双方类的对象互相持有对方,导致对象不被释放

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
//
// main.m
// 5-1类通信block
//
// Created by wanggang on 2017/8/2.
// Copyright © 2017年 hackingangle. All rights reserved.
//
#import <Foundation/Foundation.h>
#import "AClass.h"
int main(int argc, const char * argv[]) {
@autoreleasepool {
AClass *classa = [[AClass alloc] init];
[classa testBlock];
}
return 0;
}
//
// AClass.h
// 5-1类通信block
//
// Created by wanggang on 2017/8/2.
// Copyright © 2017年 hackingangle. All rights reserved.
//
#import <Foundation/Foundation.h>
#import "BClass.h"
@interface AClass : NSObject
-(void)testBlock;
@end
//
// AClass.m
// 5-1类通信block
//
// Created by wanggang on 2017/8/2.
// Copyright © 2017年 hackingangle. All rights reserved.
//
#import "AClass.h"
@implementation AClass
-(void)testBlock {
NSLog(@"testBlock from AClass");
BClass *classb = [[BClass alloc] init];
[classb testB];
}
@end
//
// BClass.h
// 5-1类通信block
//
// Created by wanggang on 2017/8/2.
// Copyright © 2017年 hackingangle. All rights reserved.
//
#import <Foundation/Foundation.h>
#import "AClass.h"
@interface BClass : NSObject
-(void)testB;
@end
//
// BClass.m
// 5-1类通信block
//
// Created by wanggang on 2017/8/2.
// Copyright © 2017年 hackingangle. All rights reserved.
//
#import "BClass.h"
@implementation BClass
-(void)testB {
NSLog(@"testB from BClass");
AClass *classa = [[AClass alloc] init];
[classa testBlock];
}
@end

block解决类之间相互通信

block解决通信中的交叉引用问题

  1. Block声明在被调用类中
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
//
// main.m
// 5-1类通信block
//
// Created by wanggang on 2017/8/2.
// Copyright © 2017年 hackingangle. All rights reserved.
//
#import <Foundation/Foundation.h>
#import "AClass.h"
int main(int argc, const char * argv[]) {
@autoreleasepool {
AClass *classa = [[AClass alloc] init];
[classa testBlock];
}
return 0;
}
//
// AClass.h
// 5-1类通信block
//
// Created by wanggang on 2017/8/2.
// Copyright © 2017年 hackingangle. All rights reserved.
//
#import <Foundation/Foundation.h>
#import "BClass.h"
@interface AClass : NSObject
-(void)testBlock;
@end
//
// AClass.m
// 5-1类通信block
//
// Created by wanggang on 2017/8/2.
// Copyright © 2017年 hackingangle. All rights reserved.
//
#import "AClass.h"
typedef void (^MyBlock) (int);
@implementation AClass
-(void)testBlock {
NSLog(@"testBlock from AClass");
BClass *classb = [[BClass alloc] init];
// MessageOfClass message = ^(NSString* msg) {
// NSLog(@"I am defined in Aclass, This outside message: %@", msg);
// };
// [classb testB:message caller:@"classa"];
[classb testB: ^(NSString* msg) {
NSLog(@"I am defined in Aclass, This outside message: %@", msg);
} caller:@"classa"];
}
@end
//
// BClass.h
// 5-1类通信block
//
// Created by wanggang on 2017/8/2.
// Copyright © 2017年 hackingangle. All rights reserved.
//
#import <Foundation/Foundation.h>
typedef void (^MessageOfClass) (NSString*);
@interface BClass : NSObject
-(void)testB:(MessageOfClass) message caller:(NSString*)caller;
@end
//
// BClass.m
// 5-1类通信block
//
// Created by wanggang on 2017/8/2.
// Copyright © 2017年 hackingangle. All rights reserved.
//
#import "BClass.h"
@implementation BClass
-(void)testB:(MessageOfClass) message caller:(NSString*)caller {
NSLog(@"caller : %@", caller);
NSLog(@"testB from BClass");
message(@"Message From BClass");
}
@end

output

1
2
3
4
5
2017-08-02 08:16:43.178927+0800 5-1类通信block[18356:1455053] testBlock from AClass
2017-08-02 08:16:43.179119+0800 5-1类通信block[18356:1455053] caller : classa
2017-08-02 08:16:43.179140+0800 5-1类通信block[18356:1455053] testB from BClass
2017-08-02 08:16:43.179165+0800 5-1类通信block[18356:1455053] I am defined in Aclass, This outside message: Message From BClass
Program ended with exit code: 0

ios基础-4-6谓词

what

按照一定的条件,对数据进行处理和过滤

how

步骤

  • 创建谓词对象
  • 设定过滤条件
  • 应用到对象上
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
//
// Person.h
// 4-6谓词对象
//
// Created by wanggang on 2017/7/28.
// Copyright © 2017年 hackingangle. All rights reserved.
//
#import <Foundation/Foundation.h>
@interface Person : NSObject
@property(nonatomic, copy)NSString *name;
@property(nonatomic, assign)int age;
@end
//
// Person.m
// 4-6谓词对象
//
// Created by wanggang on 2017/7/28.
// Copyright © 2017年 hackingangle. All rights reserved.
//
#import "Person.h"
@implementation Person
@end
//
// main.m
// 4-6谓词对象
//
// Created by wanggang on 2017/7/28.
// Copyright © 2017年 hackingangle. All rights reserved.
//
#import <Foundation/Foundation.h>
#import "Person.h"
int main(int argc, const char * argv[]) {
@autoreleasepool {
NSArray *arr1 = [[NSArray alloc] initWithObjects:@"ios", @"pc", @"android", nil];
// 相等
NSPredicate *predicate1 = [NSPredicate predicateWithFormat:@"SELF == 'pc'"];
NSArray *arr2 = [arr1 filteredArrayUsingPredicate:predicate1];
NSLog(@"%@", arr2);
// 逻辑判断
NSArray *arr3 = [[NSArray alloc] initWithObjects:@"22", @"1", @"222", nil];
NSPredicate *predicate2 = [NSPredicate predicateWithFormat:@"SELF.intValue > 10"];
NSArray *arr4 = [arr3 filteredArrayUsingPredicate:predicate2];
NSLog(@"%@", arr4);
// 关键词
NSArray *arr5 = [[NSArray alloc] initWithObjects:@"hackingangle", @"wangli", @"zhangwu", nil];
NSPredicate *predicate3 = [NSPredicate predicateWithFormat:@"SELF CONTAINS %@", @"angle"];
NSArray *arr6 = [arr5 filteredArrayUsingPredicate:predicate3];
NSLog(@"%@", arr6);
// 过滤by对象属性
Person *person1 = [[Person alloc] init];
person1.name = @"hackingangle";
person1.age = 27;
Person *person2 = [[Person alloc] init];
person2.name = @"haha";
person2.age = 17;
NSMutableArray *users = [[NSMutableArray alloc] init];
[users addObject:person1];
[users addObject:person2];
for (Person *user in users) {
NSLog(@"%@", user.name);
}
NSPredicate *predicate4 = [NSPredicate predicateWithFormat:@"age > %d", 18];
NSArray *users2 = [users filteredArrayUsingPredicate:predicate4];
for (Person *user in users2) {
NSLog(@"filtered = %@", user.name);
}
}
return 0;
}

ios基础-4-5深拷贝|浅拷贝

概念

对象拷贝分为:

  1. 浅拷贝
  2. 深拷贝

浅拷贝

  • 两个对象指向一致的内存空间
  • 只是copy了指针
  • 对象结束的时候,会调用destruct方法,这种情况下destruct会被调用2次,造成crash
  • 数据不独立
  • 释放对象不容易

深拷贝

  • 重新堆中重新申请内存空间,两个对象分别维护自己的内存空间
  • 比较容易释放对象
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
//
// Person.h
// 4-5深拷贝浅拷贝
//
// Created by wanggang on 2017/7/28.
// Copyright © 2017年 hackingangle. All rights reserved.
//
#import <Cocoa/Cocoa.h>
@interface Person : NSObject
@property(nonatomic, copy)NSString *name;
@end
//
// Person.m
// 4-5深拷贝浅拷贝
//
// Created by wanggang on 2017/7/28.
// Copyright © 2017年 hackingangle. All rights reserved.
//
#import "Person.h"
@implementation Person
-(id)copyWithZone:(NSZone*)zone{
Person *copy = [[[self class]allocWithZone:zone]init];
copy.name = [self.name copyWithZone:zone];
return copy;
}
@end
//
// main.m
// 4-5深拷贝浅拷贝
//
// Created by wanggang on 2017/7/28.
// Copyright © 2017年 hackingangle. All rights reserved.
//
#import <Foundation/Foundation.h>
#import "Person.h"
int main(int argc, const char * argv[]) {
@autoreleasepool {
Person *person1 = [[Person alloc] init];
person1.name = @"hackingangle";
Person *person2 = [person1 copy];
NSLog(@"%@", person2.name);
NSLog(@"%@ %@", person1, person2);
// 可变地址空间<->不可变地址空间
NSString *str1 = @"hackingangle";
// 浅拷贝
NSMutableString *str2 = [str1 copy];
// 深拷贝
NSMutableString *str3 = [str1 mutableCopy];
NSLog(@"%@ %@ %@", str1, str2, str3);
NSLog(@"%p %p %p", str1, str2, str3);
}
return 0;
}

ios基础-4-4-内存管理

基础概念

  • 内存
    • 计算机组成结构中的存储器,用来存储程序和数据
    • 由存储单元构成
  • 指针
    • 类实例化后,申请了内存空间,指针就是一个指向内存空间的标示,存储了内存空间的地址
    • 程序员申请的内存的存储单元
    • 先进先出
    • 系统申请的内存的存储单元
    • 先进后出

内存管理机制

内存为什么需要管理?

内存空间无论在pc下还是在手机下面都是有限的,通常几个G。

我们需要拥有一定的机制,让不使用的内存及时释放,这样系统的速度不会受到影响。

OC中受到管控的内存使用场景:

  1. NSObject类的所有子类
  2. 其他语言c,c++申请的空间

不受内存管控的场景:

  1. int,BOOL,char…等基础数据类型

内存警告

警告几次无用,IOS将直接自动收回内存,kill掉当前进程,导致app被kill

ARC模式

编译器特征,释放程序员内存管理的精力:没有强指针指向对象,对象会被销毁

对象存储的基本结构:指针、索引、引用计数

  • 引用计数
    • 对象被引用的次数,用4bytes=32bit来存
    • 初始值为0
    • alloc,new,copy 导致加1
    • retain 导致加1
    • release 导致减1
    • 如果为0,则释放

当引用技数为0时候,自动调用dealloc方法,被动调用

自动释放池

当autorealeasepool中出来的时候,对所有对象自动调用一次release,使得引用计数为0,自动回收内存空降

Runtime

C语言中在编译时期,就知道了调用顺序

  • OC语言在编译期并不知道调用顺序,是消息发送机制
    • 只要一个方法声明了,及时没有实现,在编译期也不会报错,在动态执行的时候报错
      • 比如:delegate,委托代理,委托代理中的方法有可能实现了,有可能没实现,每次调用前需要检查是否方法已经实现了
        • 委托代理中的方法有可能实现,也有可能没实现

          Runtime原理

OC如何通过发送消息实现动态调用的?

在调用的时候,会转成一个发送消息,如下:

1
2
3
[student learning];
student_msgSend(obj,@selector(doSomething));

说到消息,不得不看下OC下类的结构!

1
2
3
4
5
6
7
8
9
10
11
12
struct obj_class {
Class isa;
Class super_class;
const char *name;
long version;
long info;
long instance_size;
struct obj_ivar_list *ivars;
struct obj_method_list **methodLists;
struct obj_cache *cache;
struct objc_protocol_list *protocols;
}
  • isa
    • 最重要的指针
    • 指向静态class,存储的是静态方法
  • methodLists
    • 当前实现可以调用的方法列表
  • cache
    • 最近使用的方法的指针
    • 快速、方便、高效的访问变量

步骤:

  1. 正常的方法转消息发送
  2. 可以通过obj对象指针可以找到我们的class
    • isa->Class
  3. 先在缓存中找方法是否存在
    • cache
  4. 没有找到,则在方法列表中找
    • methodLists
  5. 找到后
    • 执行方法
    • 加入到cache缓存

使用场景

  1. 程序运行中,动态添加(修改)方法和属性
  2. 遍历类中所有方法和属性

RunLoop

  • 核心:使得程序(Thread)能够一直接收数据
  • 处理各种事件的循环
  • 不停处理调动工作和输入事件
  • 优点
    • 节省cpu效率
    • 使得线程由工作忙,没工作空闲

指针

野指针:指向不可用内存,会导致crash
空指针:内存为空

ios基础-4-3-NSDictionary

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
//
// main.m
// 4-3NSDictionary
//
// Created by wanggang on 2017/7/27.
// Copyright © 2017年 hackingangle. All rights reserved.
//
#import <Foundation/Foundation.h>
int main(int argc, const char * argv[]) {
@autoreleasepool {
// 初始化
NSDictionary *dict1 = [[NSDictionary alloc] init];
NSDictionary *dict2 = [[NSDictionary alloc] initWithObjectsAndKeys:@"2.2", @"apple", @"1.1", @"bnana", nil];
NSDictionary *dict3 = @{@"beijing":@"111.2",@"tianjian":@"38.2"};
NSLog(@"%@ %@ %@", dict1, dict2, dict3);
// 增删改查
NSString *str1 = [dict2 valueForKey:@"apple"];
NSArray *arr1 = [dict3 allKeys];
NSArray *arr2 = [dict3 allValues];
NSLog(@"%@", str1);
NSLog(@"%@ %@", arr1, arr2);
for (int i=0;i<arr1.count;i++) {
NSLog(@"%@", [dict3 valueForKey:[arr1 objectAtIndex:i]]);
}
// 遍历是key
for (NSString *item in dict3) {
NSLog(@"%@ %@", item, [dict3 valueForKey:item]);
}
// 字典数组混合使用
NSArray *arr3 = @[@"a", @"b"];
NSDictionary *dict4 = [[NSDictionary alloc] initWithObjectsAndKeys:@"v1", @"kk1", @"v22", @"kkk2", arr3, @"kkkk3", nil];
NSLog(@"%@ %@", arr3, dict4);
for (int i=0;i<[dict4 allKeys].count;i++){
NSLog(@"%@", [dict4 valueForKey:[[dict4 allKeys] objectAtIndex:i]]);
}
// 字典的增删改查
NSMutableDictionary *dict5 = [[NSMutableDictionary alloc] init];
[dict5 setValue:@"hackingangle" forKey:@"username"];
[dict5 setValue:@"27" forKey:@"age"];
NSLog(@"%@", dict5);
[dict5 setValue:@"ha" forKey:@"username"];
NSLog(@"%@", dict5);
[dict5 removeObjectForKey:@"age"];
NSLog(@"%@", dict5);
[dict5 removeAllObjects];
NSLog(@"%@", dict5);
}
return 0;
}

ios基础-4-2-NSArray

  • 有顺序
  • 有下标

创建

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
//
// main.m
// 4-2NSArray
//
// Created by wanggang on 2017/7/27.
// Copyright © 2017年 hackingangle. All rights reserved.
//
#import <Foundation/Foundation.h>
int main(int argc, const char * argv[]) {
@autoreleasepool {
NSArray *arr1 = [[NSArray alloc] init];
NSArray *arr2 = [[NSArray alloc] initWithObjects:@"a", @"b", @"c", nil];
NSArray *arr3 = @[@"a", @"b", @"c"];
NSLog(@"%@ %@ %@", arr1, arr2, arr3);
}
return 0;
}

操作

  • 增删改查
  • 长度
  • 包含
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
//
// main.m
// 4-2NSArray
//
// Created by wanggang on 2017/7/27.
// Copyright © 2017年 hackingangle. All rights reserved.
//
#import <Foundation/Foundation.h>
int main(int argc, const char * argv[]) {
@autoreleasepool {
NSArray *arr1 = [[NSArray alloc] init];
NSArray *arr2 = [[NSArray alloc] initWithObjects:@"a", @"b", @"c", nil];
NSArray *arr3 = @[@"a", @"b", @"c"];
NSLog(@"%@ %@ %@", arr1, arr2, arr3);
// 查询
NSString *str1 = [arr3 firstObject];
NSString *str2 = [arr3 lastObject];
NSString *str3 = [arr3 objectAtIndex:1];
NSLog(@"%@ %@ %@", str1, str2, str3);
NSUInteger position = [arr3 indexOfObject:@"b"];
NSLog(@"%lu", position);
// 长度
NSLog(@"length = %lu", arr2.count);
// 包含
NSLog(@"%d %d", [arr2 containsObject:@"a"], [arr2 containsObject:@"aa"]);
}
return 0;
}

不知道大家注意没有?上述没有修改、删除以及新增的操作,为什么呢?

因为我们只有在可变数组下面才能操作。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
//
// main.m
// 4-2NSArray
//
// Created by wanggang on 2017/7/27.
// Copyright © 2017年 hackingangle. All rights reserved.
//
#import <Foundation/Foundation.h>
int main(int argc, const char * argv[]) {
@autoreleasepool {
NSArray *arr1 = [[NSArray alloc] init];
NSArray *arr2 = [[NSArray alloc] initWithObjects:@"a", @"b", @"c", nil];
NSArray *arr3 = @[@"a", @"b", @"c"];
NSLog(@"%@ %@ %@", arr1, arr2, arr3);
// 查询
NSString *str1 = [arr3 firstObject];
NSString *str2 = [arr3 lastObject];
NSString *str3 = [arr3 objectAtIndex:1];
NSLog(@"%@ %@ %@", str1, str2, str3);
NSUInteger position = [arr3 indexOfObject:@"b"];
NSLog(@"%lu", position);
// 长度
NSLog(@"length = %lu", arr2.count);
// 包含
NSLog(@"%d %d", [arr2 containsObject:@"a"], [arr2 containsObject:@"aa"]);
// 删除和修改必须依赖mutableArray
NSMutableArray *arr4 = [[NSMutableArray alloc] initWithObjects:@"aa", @"bb", @"cc", @"dd", nil];
// 新增
[arr4 addObject:@"ee"];
NSLog(@"%@", arr4);
[arr4 insertObject:@"MMMMM" atIndex:1];
NSLog(@"%@", arr4);
[arr4 removeLastObject];
NSLog(@"%@", arr4);
[arr4 removeObjectAtIndex:1];
NSLog(@"%@", arr4);
[arr4 removeObject:@"cc"];
NSLog(@"%@", arr4);
[arr4 removeAllObjects];
NSLog(@"%@", arr4);
// NSString->NSArray
NSString *str4 = @"1,2,3,4,5,6,7";
NSArray *arr5 = [str4 componentsSeparatedByString:@","];
NSLog(@"%@", arr5);
NSMutableString *str5 = [[NSMutableString alloc] init];
for (NSString *item in arr5) {
[str5 appendFormat:@"%@@", item];
}
NSLog(@"%@", str5);
// NSArray<->NSMutableArray
NSArray *arr6 = @[@"a",@"b",@"c"];
// NSMutableArray *arr7 = arr6;
NSMutableArray *arr7 = [[NSMutableArray alloc] initWithArray:arr6];
NSArray *arr8 = arr7;
NSLog(@"%@ %@ %@", arr6, arr7, arr8);
}
return 0;
}

ios基础-4-1-NSString

字符串创建、比较、搜索、获取子字符串、转换大小写、转换首字母、增删改查、trim

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
//
// main.m
// 4-1字符串
//
// Created by wanggang on 2017/7/27.
// Copyright © 2017年 hackingangle. All rights reserved.
//
#import <Foundation/Foundation.h>
int main(int argc, const char * argv[]) {
@autoreleasepool {
// 1.创建字符串
NSString *str1 = [[NSString alloc] init];
NSString *str2 = @"str2";
NSLog(@"%@ %@", str1, str2);
// 2.基础数据类型->字符串
NSString *str3 = [[NSString alloc] initWithFormat:@"%f", 2.2];
NSString *str4 = [[NSString alloc] initWithFormat:@"%d", 2];
NSLog(@"%@ %@", str3, str4);
// 字符串->基础数据类型
NSLog(@"%f %d", str3.floatValue, str4.intValue);
// 3.字符串的比较
NSString *str5 = @"abc";
NSString *str6 = @"abc";
NSString *str7 = [[NSString alloc] initWithFormat:@"%@", @"abc"];
// 相同的值
if ([str5 isEqualToString:str6]) {
NSLog(@"str5 str6 is equal.");
}
// 相同的指针,相同的值
if (str6 == str5) {
NSLog(@"str5 str6 all equal(value, quote pointer)");
}
// 不同的指针,相同的值
if (str5 == str7) {
NSLog(@"str5 str7 all equal(value, quote pointer)");
}
// 4.字符串大小写,首字母大写
NSString *str8 = @"hacking angle";
NSLog(@"%@", [str8 uppercaseString]);
NSLog(@"%@", [str8 lowercaseString]);
NSLog(@"%@", [str8 capitalizedString]);
// 5.字符串内容索引
NSString *str9 = @"abcedf12345";
NSString *str10 = @"edf1";
NSRange range;
range = [str9 rangeOfString:str10];
NSLog(@"lenth = %lu location = %lu", range.length, range.location);
// 6.字符串位置索引
NSString *str11 = @"abcdef12345";
NSRange range2;
range2.location = 1;
range2.length = 2;
NSString *str12 = [str11 substringWithRange:range2];
NSLog(@"%@", str12);
// 7.字符串增删改查
NSString *str13 = @"a";
NSString *str14 = [str13 stringByAppendingString:@"b"];
NSString *str15 = [str13 stringByAppendingFormat:@"%d %f", 1, 1.1];
NSLog(@"%@ %@ %@", str13, str14, str15);
NSString *str16 = [str13 stringByReplacingOccurrencesOfString:@"a" withString:@"e"];
NSLog(@"%@", str16);
// 8.可变字符串
NSMutableString *str17 = [[NSMutableString alloc] initWithString:@"abc"];
[str17 appendString:@"1"];
[str17 insertString:@"@hackingangle..." atIndex:1];
[str17 appendFormat:@"%d", 10000];
NSLog(@"%@", str17);
// 9.字符串内容检查
NSString *str18 = @"http://www.baidu.com/logo.png";
if ([str18 containsString:@"http://"]) {
NSLog(@"http协议");
}
if ([str18 hasPrefix:@"http://"]) {
NSLog(@"以http开头");
}
if ([str18 hasSuffix:@".png"]) {
NSLog(@"是一张图");
}
// 10去空白
NSString *str19 = @" aa ";
NSString *str20 = [str19 stringByTrimmingCharactersInSet:[NSCharacterSet whitespaceCharacterSet]];
NSLog(@"%@ %@", str19, str20);
NSLog(@"%lu %lu", str19.length, str20.length);
}
return 0;
}

ios基础-3-6继承多态

继承

继承父类所有的属性和方法

多态

相同的方法,不同的表现行为在不同的场景下

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
//
// main.m
// 3-6继承多态
//
// Created by wanggang on 2017/7/26.
// Copyright © 2017年 hackingangle. All rights reserved.
//
#import <Foundation/Foundation.h>
#import "Person.h"
#import "Student.h"
#import "Teacher.h"
int main(int argc, const char * argv[]) {
@autoreleasepool {
Person *person = [[Person alloc] init];
[person hi];
// 继承
Student *stu = [[Student alloc] init];
[stu hi];
Teacher *teacher = [[Teacher alloc] init];
[teacher hi];
// 多态
// Person *person2 = [[Student alloc] init];
Person *person2 = [[Teacher alloc] init];
[person2 my];
}
return 0;
}
//
// Person.h
// 3-6继承多态
//
// Created by wanggang on 2017/7/26.
// Copyright © 2017年 hackingangle. All rights reserved.
//
#import <Foundation/Foundation.h>
@interface Person : NSObject
-(void)hi;
-(void)my;
@end
//
// Person.m
// 3-6继承多态
//
// Created by wanggang on 2017/7/26.
// Copyright © 2017年 hackingangle. All rights reserved.
//
#import "Person.h"
@implementation Person
-(void)hi{
NSLog(@"hi in person");
}
-(void)my{
NSLog(@"my in person");
}
@end
//
// Student.h
// 3-6继承多态
//
// Created by wanggang on 2017/7/26.
// Copyright © 2017年 hackingangle. All rights reserved.
//
#import <Foundation/Foundation.h>
#import "Person.h"
@interface Student : Person
@end
//
// Student.m
// 3-6继承多态
//
// Created by wanggang on 2017/7/26.
// Copyright © 2017年 hackingangle. All rights reserved.
//
#import "Student.h"
@implementation Student
-(void)my{
NSLog(@"my in student");
}
@end
//
// Teacher.h
// 3-6继承多态
//
// Created by wanggang on 2017/7/26.
// Copyright © 2017年 hackingangle. All rights reserved.
//
#import "Person.h"
@interface Teacher : Person
@end
//
// Teacher.m
// 3-6继承多态
//
// Created by wanggang on 2017/7/26.
// Copyright © 2017年 hackingangle. All rights reserved.
//
#import "Teacher.h"
@implementation Teacher
-(void)my{
NSLog(@"my in teacher");
}
@end

ios基础-3-5分类|类扩展

分类

分类:类的扩展,不知道原来类的情况下,新增方法,但是不可以添加属性

!!! 方法名相同,分类中方法优先级高,会覆盖之前的方法

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
//
// main.m
// 3-5分类|扩展
//
// Created by wanggang on 2017/7/26.
// Copyright © 2017年 hackingangle. All rights reserved.
//
#import <Foundation/Foundation.h>
#import "Person.h"
// 分类
#import "Person+Student.h"
int main(int argc, const char * argv[]) {
@autoreleasepool {
Person *person = [[Person alloc] init];
[person eating];
// 分类
[person learning];
}
return 0;
}
//
// Person.h
// 3-5分类|扩展
//
// Created by wanggang on 2017/7/26.
// Copyright © 2017年 hackingangle. All rights reserved.
//
#import <Foundation/Foundation.h>
@interface Person : NSObject
-(void)eating;
@end
//
// Person.m
// 3-5分类|扩展
//
// Created by wanggang on 2017/7/26.
// Copyright © 2017年 hackingangle. All rights reserved.
//
#import "Person.h"
@implementation Person
-(void)eating{
NSLog(@"person eating...");
}
@end
//
// Person+Student.h
// 3-5分类|扩展
//
// Created by wanggang on 2017/7/26.
// Copyright © 2017年 hackingangle. All rights reserved.
//
#import "Person.h"
@interface Person (Student)
-(void)learning;
@end
//
// Person+Student.m
// 3-5分类|扩展
//
// Created by wanggang on 2017/7/26.
// Copyright © 2017年 hackingangle. All rights reserved.
//
#import "Person+Student.h"
@implementation Person (Student)
-(void)learning{
NSLog(@"learning is person what person");
}
@end

类扩展

想扩展属性,必须用类扩展

同一个.h文件中只能定义一个@interface标签,所以类扩展我们必须放到.m文件中

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
//
// main.m
// 3-5分类|扩展
//
// Created by wanggang on 2017/7/26.
// Copyright © 2017年 hackingangle. All rights reserved.
//
#import <Foundation/Foundation.h>
#import "Person.h"
// 分类
#import "Person+Student.h"
int main(int argc, const char * argv[]) {
@autoreleasepool {
Person *person = [[Person alloc] init];
[person eating];
// 分类
[person learning];
}
return 0;
}
//
// Person.h
// 3-5分类|扩展
//
// Created by wanggang on 2017/7/26.
// Copyright © 2017年 hackingangle. All rights reserved.
//
#import <Foundation/Foundation.h>
@interface Person : NSObject
-(void)eating;
@end
//
// Person.m
// 3-5分类|扩展
//
// Created by wanggang on 2017/7/26.
// Copyright © 2017年 hackingangle. All rights reserved.
//
#import "Person.h"
@interface Person() {
BOOL male;
}
@end
@implementation Person
-(id)init{
self = [super init];
if (self) {
male = true;
}
return self;
}
-(void)eating{
if (male) {
NSLog(@"male");
} else {
NSLog(@"female");
}
NSLog(@"person eating...");
}
@end
//
// Person+Student.h
// 3-5分类|扩展
//
// Created by wanggang on 2017/7/26.
// Copyright © 2017年 hackingangle. All rights reserved.
//
#import "Person.h"
@interface Person (Student)
-(void)learning;
@end
//
// Person+Student.m
// 3-5分类|扩展
//
// Created by wanggang on 2017/7/26.
// Copyright © 2017年 hackingangle. All rights reserved.
//
#import "Person+Student.h"
@implementation Person (Student)
-(void)learning{
NSLog(@"learning is person what person");
}
@end
,