iOS经典面试题(持续更新)

 前言

最近所在的公司项目下线了,整个移动部门直接全部解散,于是乎博主又开始了新的征程, 明天会3家公司(其中有摇滚河马网络科技有限公司,camera360),这两家公司我都很喜欢,于是乎为我收集了网上的部分经典面试题,以便明日迎战。

什么是ARC?

参考答案:

1.arc是自动引用计数器

ARC的要点:在对象被创建时retain 的数量+1,在对象被release时,retain的数量-1,当retain的数量为0时,对象被销毁程序中加入autoreleasepool的对象会自动加上autoreleasepool方法,该对象的retain为0时,对象被销毁。

2.autoreleasepool和runLoop的关系:

autoreleasepool本质上是延迟释放,延迟调用release,对于每一个runLoop,系统都会创建一个autoreleasepool,需要销毁的对象放入autoreleasepool中,当每一次runLoop的循环结束时,autoreleasepool会被销毁,于是乎autoreleasepool内的每一个对象都会被release,从而达到销毁对象的目的。

在进行循环创建临时变量的时候,考虑到ARC的对象的回收机制,ARC对象的回收是在runLoop进行睡眠状态之前进行释放的,所以最好加上@autoreleasepool,防止内存泄漏

keywords的区别: assign和 weak, __block 和__weak

assgin一般用于基本类型,week用于oc对象,属于弱引用。

assign其实也可以用来修饰对象,那么我们为什么不用它呢?因为被assign修饰的对象在释放之后,指针的地址还是存在的,也就是说指针并没有被置为nil。如果在后续的内存分配中,刚好分到了这块地址,程序就会崩溃掉。 
而weak修饰的对象在释放之后,指针地址会被置为nil。所以现在一般弱引用就是用weak。

__block:一个变量被__block修饰,此变量可以在block中修改其值,并且在block中对其进行赋值不会被强引用。

__block在ARC和 非ARC下都可以使用,可以修饰基本数据类型。

__weak只能在ARC模式使用,而且只能修饰对象,不能修饰基本数据类型

__block对象可以在block中重新进行赋值,__weak不能重新进行赋值。

使用atomic一定是线程安全的?

不是的。 
atomic原子操作,系统会为setter方法加锁。 具体使用 @synchronized(self){//code } 
nonatomic不会为setter方法加锁。 
atomic:线程安全,需要消耗大量系统资源来为属性加锁 
nonatomic:非线程安全,适合内存较小的移动设备

+(void)load; +(void)initialize;有什么用处?

在Objective-C中,runtime会自动调用每个类的两个方法。+load会在类初始加载时调用,+initialize会在第一次调用类的类方法或实例方法之前被调用。这两个方法是可选的,且只有在实现了它们时才会被调用。 
共同点:两个方法都只会被调用一次。

objective c调用方法为嘛叫做给对象发消息?

看看大佬的回答 http://www.jianshu.com/p/620022378e97

UIView和CALayer是啥关系?

我的理解:view负责交互数据,layer负责显示UI。

 如何高性能的给UIImageView加个圆角?

 大佬的解释 http://www.cocoachina.com/ios/20160301/15486.html

 

步骤: 
  a、创建目标大小(cropWidth,cropHeight)的画布。

  b、使用UIImage的drawInRect方法进行绘制的时候,指定rect为(-x,-y,width,height)。

  c、从画布中得到裁剪后的图像。

- (UIImage*)cropImageWithRect:(CGRect)cropRect

{

    CGRect drawRect = CGRectMake(-cropRect.origin.x , -cropRect.origin.y, self.size.width * self.scale, self.size.height * self.scale);


    UIGraphicsBeginImageContext(cropRect.size);

    CGContextRef context = UIGraphicsGetCurrentContext();

    CGContextClearRect(context, CGRectMake(0, 0, cropRect.size.width, cropRect.size.height));


    [self drawInRect:drawRect];


    UIImage *image = UIGraphicsGetImageFromCurrentImageContext();

    UIGraphicsEndImageContext();


    return image;

}


@end

 APP性能优化

APP性能优化请参考

 

loadView是干嘛用的?

当你访问一个ViewController的view属性时,如果此时view的值是nil,那么,ViewController就会自动调用loadView这个方法。这个方法就会加载或者创建一个view对象,赋值给view属性。 
loadView默认做的事情是:如果此ViewController存在一个对应的nib文件,那么就加载这个nib。否则,就创建一个UIView对象。

如果你用Interface Builder来创建界面,那么不应该重载这个方法。

如果你想自己创建view对象,那么可以重载这个方法。此时你需要自己给view属性赋值。你自定义的方法不应该调用super。如果你需要对view做一些其他的定制操作,在viewDidLoad里面去做。

=========================================

根据上面的文档可以知道,有两种情况:

1、如果你用了nib文件,重载这个方法就没有太大意义。因为loadView的作用就是加载nib。如果你重载了这个方法不调用super,那么nib文件就不会被加载。如果调用了super,那么view已经加载完了,你需要做的其他事情在viewDidLoad里面做更合适。

2、如果你没有用nib,这个方法默认就是创建一个空的view对象。如果你想自己控制view对象的创建,例如创建一个特殊尺寸的view,那么可以重载这个方法,自己创建一个UIView对象,然后指定 self.view = myView; 但这种情况也没有必要调用super,因为反正你也不需要在super方法里面创建的view对象。如果调用了super,那么就是浪费了一些资源而已 
参考:http://www.cnblogs.com/dyllove98/archive/2013/06/06/3123005.html

16. viewWillLayoutSubView viewDidLayoutSubviews

横竖屏切换的时候,系统会响应一些函数,其中 viewWillLayoutSubviews 和 viewDidLayoutSubviews。

- (
void
)viewWillLayoutSubviews


{


     [
self
 _shouldRotateToOrientation:(UIDeviceOrientation)[
UIApplication
 sharedApplication]
.statusBarOrientation
];


}


-(
void
)_shouldRotateToOrientation:(UIDeviceOrientation)orientation {

        
if
 (orientation == UIDeviceOrientationPortrait ||orientation ==

                UIDeviceOrientationPortraitUpsideDown) {

          
// 竖屏

}

else
 {

         
// 横屏

    }

}

 

GCD里面有哪几种Queue?

1.主队列 dispatch_main_queue(); 串行 ,更新UI 
2.全局队列 dispatch_global_queue(); 并行,四个优先级:background,low,default,high 
3.自定义队列 dispatch_queue_t queue ; 可以自定义是并行:DISPATCH_QUEUE_CONCURRENT或者串行DISPATCH_QUEUE_SERIAL

 

赞一个 (1)
分享到: +More

评论 沙了个发

换个身份

取消评论