您的位置:首页 > 移动开发 > Objective-C

Objective-C知识点整理(常见面试知识点)

2017-07-31 15:13 260 查看

1. copy和mutablecopy。这个问题大家应该都遇到过,大多数面试官都会问到这个问题,或深或浅而已。

这个问题一般是从深浅拷贝延伸过来的,简单来说浅拷贝只是对指向对象的指针的拷贝,而深拷贝不仅是对指针的拷贝,同时也将对象本身进行拷贝。

copy:需要遵循NSCopying协议,是调用copyWithZone方法得到的一个不可变对象。自定义类需要实现NSCopying协议,并重写copyWithZone方法。

mutableCopy: 需要遵循NSMutableCopying协议,是调用mutableCopyWithZone方法得到的一个可变对象。自定义类需要实现NSMutableCopying协议,并重写mutableCopyWithZone方法。

下面我们先用一段测试代码来看看NSString和NSMutableString调用copy和mutuableCopy方法后对象的拷贝情况。

NSString *str = [[NSString alloc] initWithString:@"Hello"];
NSString *strCopy = [str copy];
NSString *strMutableCopy = [str mutableCopy];

NSLog(@"           str pointer: %p",&str);
NSLog(@"       strCopy pointer: %p",&strCopy);
NSLog(@"strMutableCopy pointer: %p",&strMutableCopy);

NSLog(@"           str: %p",str);
NSLog(@"       strCopy: %p",strCopy);
NSLog(@"strMutableCopy: %p",strMutableCopy);

NSMutableString *mutStr = [[NSMutableString alloc] initWithString:@"World"];
NSMutableString *mutStrCopy = [str copy];
NSMutableString *mutStrMutableCopy = [str mutableCopy];

NSLog(@"           mutStr: %p",mutStr);
NSLog(@"       mutStrCopy: %p",mutStrCopy);
NSLog(@"mutStrMutableCopy: %p",mutStrMutableCopy);

NSArray *arr = [NSArray arrayWithObjects:@"1",@"2", nil];
NSArray *copyArr = [arr copy];
NSArray *mutableArr = [arr mutableCopy];

NSLog(@"arr pointer: %p",&arr);
NSLog(@"copyArr pointer: %p",©Arr);
NSLog(@"mutableArr pointer: %p",&mutableArr);

NSLog(@"arr : %p",arr);
NSLog(@"copyArr : %p",copyArr);
NSLog(@"mutableArr : %p",mutableArr);

NSLog(@"arr0 : %p",arr[0]);
NSLog(@"copyArr0 : %p",copyArr[0]);
NSLog(@"mutableArr0 : %p",mutableArr[0]);


运行结果是:

str pointer: 0x7fff55b579a8
strCopy pointer: 0x7fff55b579a0
strMutableCopy pointer: 0x7fff55b57998

str: 0x10a0a9090
strCopy: 0x10a0a9090
strMutableCopy: 0x610000077380

mutStr: 0x60000007b500
mutStrCopy: 0x10a0a9090
mutStrMutableCopy: 0x60000007b200

arr pointer: 0x7fff55b57978
copyArr pointer: 0x7fff55b57970
mutableArr pointer: 0x7fff55b57968

arr : 0x61000002a880
copyArr : 0x61000002a880
mutableArr : 0x61000005f1a0

arr0 : 0x10a0a91f0
copyArr0 : 0x10a0a91f0
mutableArr0 : 0x10a0a91f0


由此可见:

classescopymutableCopy
NSString浅拷贝,只是复制了指针深拷贝,生成一个新的可变对象
NSMutableString深拷贝,生成一个新的不可变对象深拷贝,生成一个新的可变对象
NSArray浅拷贝,只是复制了指针深拷贝,生成一个新的可变对象
但是NSArray中的对象是没有被拷贝的,要想拷贝Array中的数据必须对每个对象进行拷贝,前提是对象必须遵守相应的协议。

2.instancetype和id的区别。

首先id类型的引入是因为要支持OC的动态类型;关于动态类型和静态类型后面再做介绍。

id类型可以指向任意一种指向类的对象,因此它既可以作为函数的参数类型,也可以作为返回值的类型。在编译时不会检查类型。

instancetype类型只能作为返回值类型,返回方法所在类相同类型的对象,在编译时会进行类型检查。

使用的过程中的建议就是构造方法全都使用instancetype类型。

3. 静态数据类型和动态数据类型

(1)静态数据类型的特点:

在编译时就知道变量的类型, 知道变量中有哪些属性和方法 在编译的时候就可以访问这些属性和方法, 并且如果是通过静态数据类型定义变量, 如果访问了不属于静态数据类型的属性和方法, 那么编译器就会报错

(2)动态数据类型的特点:

在编译的时候编译器并不知道变量的真实类型, 只有在运行的时候才知道它的真实类型, 并且如果通过动态数据类型定义变量, 如果访问了不属于动态数据类型的属性和方法, 编译器不会报错

4. autorelease 自动释放池

(1)什么是自动释放池?

autorelease是一种支持引用计数的内存管理方式,只要给对象发送一条autorelease消息,会将对象放到一个自动释放池中,当自动释放池被销毁时,会对池子里面的所有对象做一次release操作

(2)自动释放池的优点是什么?

不需要再手动去管理对象生存周期,何时去进行release操作。

(3)简述自动释放池的原理?

autorelease实际上只是把对release的调用延迟了,对于每一个autorelease,系统只是把该 Object放入了当前的autorelease pool中,当该pool被释放时,该pool中的所有Object会被调用Release。

(4)自动释放池有哪些注意事项?

<1>在自动释放池中创建了对象, 一定要调用autorelease,才会将对象放入自动释放池中

<2>一个程序中可以创建N个自动释放池, 并且自动释放池还可以嵌套

<3>不要再自动释放池中使用比较消耗内存的对象, 占用内存比较大的对象

<4>尽量不要再自动释放池中使用循环, 特别是循环的次数非常多, 并且还非常占用内存

<5>千万不要写多次autorelease

<6>一个alloc/new对应一个autorelease或者release

(5)自动释放池是以什么形式存储的?

如果存在多个自动释放池的时候, 自动释放池是以 “栈” 的形式存储在堆区

5. ARC内存管理

(1):ARC的原理是什么?

当ARC开启时,编译器将自动在代码合适的地方插入retain, release和autorelease,而我们则完全不需要担心自己管理不好内存而导致内存泄漏等问题。

(2)ARC有什么优点?

免除了手动管理内存的烦琐,如果不错用的话基本上能够
a950
避免内存泄露

(3)ARC的原则是什么?什么是强指针?什么是弱指针?

只要还有一个强指针变量指向对象,对象就会保持在内存中

<1>强指针

默认所有指针变量都是强指针

被__strong修饰的指针

<2>弱指针

被__weak修饰的指针

(3)ARC下@property修饰符有哪些?

strong : 用于OC对象, 相当于MRC中的retain

weak : 用于OC对象, 相当于MRC中的assign

assign : 用于基本数据类型, 跟MRC中的assign一样

6. 如何解决block中的循环引用?

如果block内引用了对象本身,或者导致了A引用了B,B又引用了A的情形,导致两个对象互相引用,引用计数永远不能变成0而无法释放的情况。

解决循环引用可以在block对象外面设为weak:__weak __typeof(self) weakSelf = self;

如果block内的某些使用weakSelf的代码执行的比较晚,则weakSelf可能已经被释放了而导致崩溃,所以需要将weakSelf设为strong: __strong __typeof(self) strongSelf = weakSelf; strongSelf是一个自动变量当block执行完毕就会被释放掉,不会对self进行一直进行强引用。

7. 判断一个数是整数还是小数的小技巧

float a = 3.4;
if (a == (int)a) {
NSLog(@"is int");
}
else{
NSLog(@"not int");
}
输出 "not int"
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签:  面试 oc基础 内存 iOS