iOS开发中调试的总结

本博客转自:http://www.jianshu.com/p/9c4c92a38468

【1.普通断点】

断点(Breakpoint)绝对是调试程序的第一大选择,也是掌握的基础技能。顾名思义,当程序运行到断点处时会暂停运行。比如断点打在11行,那么程序就会停在11行(注意:程序只运行到了前10行,第11行其实还没有被执行!!!)。只要在代码行旁边点击,就能添加一个断点,再次点击,就能让断点不可用(disable了,仍然存在,只是不起作用了)。在某一行创建断点的快捷键是:command+\

并能在调试过程中在下方看到参数的值:

【2.条件断点】

以上的断点只是最普通的,我们还能对断点的属性进行配置,设置条件,使断点更加智能化,右键断点进入编辑对话框:

我以一个循环作为测试代码:

循环中的代码每次都要单步执行,可能这并不是我想要的。我想要在i为3的时候中断程序,进行调试,编写条件如下:

设置i==3的条件后,程序就会在该条件时中断,而不会每次到达该位置都中断。中断时输出如下:

同时也可以设置Ignore参数,会忽略前面n次的断点运行,会在第n+1次中断。

调试输出如下:

同时,还可以查看某个函数被调用的次数,设置Action参数如下,注意要选中Automatically continue after evaluating actions.

输出结果如下:

【3.异常断点】

断点的功能不限于上面所述。开发iOS知道,如果我们因为异常然后程序crash了,代码就直接跑到main.m的main函数中去了。为什么就不能跑到出现异常的代码中呢???异常断点就为我们解决该问题,程序就会在异常出现的那行代码终止。创建异常断点图例如下:

如下所示就创建完成了。如果碰到异常crash时,尝试使用异常断点吧。

【4.符号断点Symbolic Breakpoint】

符号断点的创建也同异常断点。一般符号断点可以在你指定的[类名 方法名]时中断执行。

配置符号断点如下:可以当执行到ViewController类的viewDidLoad方法时中断执行。

如果你的Symbol只写了一个函数名,那么就会在出现该函数名的地方就中断执行。如下,就会在运行到doAnimation的时候中断。是不是很强大呢?

【5.Analyze分析器】

Analyze分析器是一种静态的工具,可以对我们的程序进行分析,找出我们未使用的变量,或一些死存储。执行Analyze如下:Product-->Analyze. 如下蓝色的标记就是静态分析的结果。

当然,我们可以设置在编译程序的时候同时Analyze,把下列选项设为Yes即可。

【6.Profile检查器】

这个工具实在是太NB了,三言两语说不完,贴张图,大家感受一下,我会在以后的博客中慢慢讲解该工具的使用。同样在Product-->Profile中打开。

【7.僵尸对象】

iOS中把那些已经release但还没完全消失的对象叫做僵尸对象,对已经release的对象再次释放,就会发生异常。虽然自从使用ARC后,由于对象释放产生的异常已经大大变少,但偶尔还会出现。开启僵尸对象模式后,就能快速定位到异常位置。开启方式如下:Product-->Scheme-->Edit Scheme. 勾选Enable Zombie Objects即可。

【8.lldb命令】

Xcode中使用llvm编译器,公认为最好的C、C++、OC、Swift编译器。而lldb是llvm中的调试器,我们可以使用一些简单的命令进行调试,我还是把上面的循环代码作为测试代码。

断点调试中,使用po命令、print命令在Console控制台打印出变量信息:

【9.NSLog打印】

应该说NSLog打印信息是初学者最喜欢的调试手法,也是最简单的调试,通过打印出的信息查看程序运行的路径。但是打印出的信息较少,本身NSLog效率较低,有人使用宏做了部分优化,代码如下:能够打印出所在类名、所在方法名、详细时间、行号。

#import "ViewController.h"

#define NSLog(format, ...) do { \

fprintf(stderr, " %s\n", \

[[[NSString stringWithUTF8String:__FILE__] lastPathComponent] UTF8String], \

__LINE__, __func__); \

(NSLog)((format), ##__VA_ARGS__); \

fprintf(stderr, "-------\n"); \

} while (0)

@interface ViewController ()

@end

@implementation ViewController

- (void)viewDidLoad {

[super viewDidLoad];

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

NSLog(@"我的值:%d",i);

}

}

@end

打印结果如下:

【10.生命周期方法init,dealloc】

对于ViewController来说,有两个生命周期函数我们可以进行重写,也就是init和dealloc方法。对于某些对象的状态,我们可以在这两个方法中查看。尤其是在dealloc中可以看到当ViewController退出的时候某个对象是否release。

- (instancetype)init

{

self = [super init];

if (self) {

//初始化语句;

}

return self;

}

- (void)dealloc

{

//释放后调用;

}

【11.查看代码运行时间】

有时候我们想要准确的知道某段代码、某个循环执行的时间,然后分析效率等问题,这个时候就需要执行时间是多少。正好看到网上已经有人做了这个工作,我就直接摘下来了。正好也用了宏的方式计算时间,我们只要在需要计算时间的代码块前后写上TICK,TOCK宏即可。当然,原理也是非常的简单,也就是使用NSDate计算差值。

#import "ViewController.h"

#define TICK  NSDate *startTime = [NSDate date]

#define TOCK  NSLog(@"Time: %f", -[startTime timeIntervalSinceNow])

@interface ViewController ()

@end

@implementation ViewController

- (void)viewDidLoad {

[super viewDidLoad];

TICK;

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

NSLog(@"我的值:%d",i);

}

TOCK;

}

@end

打印结果如下:

【12.手机截屏】

手机截屏也算调试?哈哈。其实也算是开发中的一个小技巧哈。其实大家都会在iPhone上同时按电源键+Home键截屏,然后使用各种通讯软件发给其他人,这个略显不方便。我们来使用Xcode中的方式截屏。当手机接上电脑后,注意要把调试设备选为自己的手机:

然后选择Debug-->View Debugging-->Take Screenshot...  .然后可以看到手机屏幕已经在你的电脑桌面了。是不是比直接在手机上操作方便多了呢?这样就可以快速的发给其他开发者、PM等人了。

【13.viewDidLoad不建议写太多代码】

个人建议不要在viewDidLoad方法中写入太多代码。尤其是涉及该界面中的动画的时候,因为执行viewDidLoad方法的时候,界面可能还没完全加载出来,如果此时把动画放在viewDidLoad中,可能会造成动画无法显示。当然也不建议把耗时的网络请求和动画效果都放在viewDidLoad中,界面的阻塞也会造成动画无法显示。可以尝试把动画放在viewDidAppear,viewWillAppear方法中。对于这类涉及UI的问题,调试也是比较麻烦的。。。

【14.视图调试】

如今iOS开发的UI设计有很多种方式,比如storyboard,xib,代码实现。对于stoayboard,xib可视化实现是比较简单的,但是对于一些“iOS老程序员”而言,都喜欢使用代码实现UI,并且可能UI层次还比较复杂。这样就给我们新接手项目的开发者带来很多困扰。如何快速查看一个复杂UI的界面层次和布局,最快的方法就是用到视图调试。

当项目运行到某一个界面(可以是模拟器或真机)时,开启视图调试,点击按钮如图:

这样就会进入试图调试,你可以很方便的查看这个界面。这里可以看到控件之间的层次关系。

左侧的树形层次图可以在查看线程、队列和UI之间切换:

【15】常用的编译宏定义:可以让代码在不同的编译情况下执行。

(1)__OPTIMIZE__  :用于release和debug的判断,当选择了__OPTIMIZE__  时,可以让代码在release时执行,在debug时不执行。示例如下:

#ifndef __OPTIMIZE__

//这里执行的是debug模式下

else

//这里执行的是release模式下

#endif

(2)__i386__ 与 __x86_64__  :用于模拟器环境和真机环境的判断。满足该条件的代码只在模拟器下执行。示例代码如下:

#if defined (__i386__) || defined (__x86_64__)

//模拟器下执行

#else

//真机下执行

#endif

(3)__IPHONE_OS_VERSION_MAX_ALLOWED  :当前编译的SDK版本,可以与__IPHONE_9_0等宏定义进行比较,进行不同版本下代码的执行。示例如下:

if (__IPHONE_OS_VERSION_MAX_ALLOWED == __IPHONE_9_0) {

//如果当前SDK版本为9.0是执行这里的代码

}else{

//否则执行这里

}

【16】预编译宏 #ifdef    #else  #endif

#ifdef ****

//代码1

else

//代码2

#endif

意思是 如果标识符****已被#define命令定义过,则对代码1进行编译,否则对代码2进行编译。

同时也有#ifndef,则与#ifdef刚好相反。

时间: 2024-10-10 00:09:35

iOS开发中调试的总结的相关文章

iOS开发——淫技篇&amp;iOS开发中各种淫技总结(六)

iOS开发中各种淫技总结(六) swift中指针的使用 在 Swift 中,指针都使用一个特殊的类型来表示,那就是 UnsafePointer<T>.遵循了 Cocoa 的一贯不可变原则,UnsafePointer<T> 也是不可变的.当然对应地,它还有一个可变变体,UnsafeMutablePointer<T>.绝大部分时间里,C 中的指针都会被以这两种类型引入到 Swift 中:C 中 const 修饰的指针对应 UnsafePointer (最常见的应该就是 C

ios 开发中 动态库 与静态库的区别

使用静态库的好处 1,模块化,分工合作 2,避免少量改动经常导致大量的重复编译连接 3,也可以重用,注意不是共享使用 动态库使用有如下好处: 1使用动态库,可以将最终可执行文件体积缩小 2使用动态库,多个应用程序共享内存中得同一份库文件,节省资源 3使用动态库,可以不重新编译连接可执行程序的前提下,更新动态库文件达到更新应用程序的目的. 从1可以得出,将整个应用程序分模块,团队合作,进行分工,影响比较小. 等其他好处, 从2可以看出,其实动态库应该叫共享库,那么从这个意义上来说,苹果禁止iOS开

iOS开发中使用宏定义提高开发效率

iOS开发中使用宏定义提高开发效率 (2013-07-10 10:47:33) 转载▼ iOS开发中,巧妙的使用宏定义,可以提高开发效率,本篇简单介绍一下宏的定义,设置,应用,并在未来实践中不断追加一些常用的宏定义. 调试Log iPhone应用程序开发调试的时候,在代码中加入NSLog的暴力调试方法是很频繁的,但是在release的时候要删除这些调试代码,那工作量是烦躁,这样的情况下,试用宏就会显得非常的方便. 看下面的例子: #ifdef DEBUG #define LOG(...) NSL

iOS开发——淫技篇&amp;iOS开发中各种淫技总结(五)

淫技篇&iOS开发中各种淫技总结(五) ARC的使用: ARC并不能避免所有的内存泄露.使用ARC之后,工程中可能还会有内存泄露,不过引起这些内存泄露的主要原因是:block,retain循环,对CoreFoundation对象(通常是C结构)管理不善,以及真的是代码没写好. reuseIdentifier 在iOS程序开发中一个普遍性的错误就是没有正确的为UITableViewCells.UICollectionViewCells和UITableViewHeaderFooterViews设置r

IOS开发中重写init方法使用需谨慎

IOS开发中重写init方法使用需谨慎 今天在写一个小软件的时候出现一点问题,这个软件的功能是搜索全国学校,首页就是搜索输入框,在框中输入完要查询的学校所在省份,点击buttom后就会跳转到对应的视图控制器中,然后把搜索结果呈现在一个TableView上,但是我在调试时,每次输入完然后点击搜索按钮时,弹出结果列表总是空的,我需要返回到首页再点击一次搜索才会出现结果,而且我在首页更改搜索关键字之后,点击搜索,结果还是上次的搜索结果,必须返回点击一次才会出现这次的搜索结果. 经过大神指点,原来这个问

【Swift】图文混排,ios开发中在textfield或textView中插入图片

在ios开发中,我们一般都是在textfield或者textView中输入文字.当我们需要插入图片的时候其实也是很简单的 我们需要利用的textfield,textView的属性化文本,将图片以附件的形式插入 步骤如下:(以textView为了,oc中也是一样的) 创建附件,同时设置好textView的字体大小(或者在storyBoard中设置) 1 //设置字体 2 textView.font = UIFont.systemFontOfSize(24) 3 //创建附件 4 let attac

iOS开发中,怎么打包为ipa格式的软件包以及怎么安装到手机终端上

iOS开发中,怎么打包为ipa格式的软件包以及怎么安装到手机终端上. (我的开发环境为Xcode6.1.1 ) 作为个人开发者(当然我的开发者帐号为个人开发者帐号,而不是企业开发者帐号),对于自己来说,我们只需要真机调试就可以将应用安装到自己的手机上:如果你在发布前想给更多的测试或朋友使用你的APP(关键是他们并不在你的身边,如果在你的身边,你当然可以通过真机调试一个一个的将应用安装到他们的手机上:此时你的APP还没有上线,Appstore还没有),你该怎么做呢?想想吧! 在开发者中心中,你可能

iOS开发中遇到的一些问题及解决方案【转载】

iOS开发中遇到的一些问题及解决方案[转载] 2015-12-29 [385][scrollView不接受点击事件,是因为事件传递失败] // //  MyScrollView.m //  Created by beyond on 15/6/6. //  Copyright (c) 2015年 beyond.com All rights reserved. //  不一定要用继承,可以使用分类 #import "MyScrollView.h" #import "CoView.

ios开发中的4种数据持久化方式【二、数据库 SQLite3、Core Data 的运用】

               在上文,我们介绍了ios开发中的其中2种数据持久化方式:属性列表.归档解档.本节将继续介绍另外2种iOS持久化数据的方法:数据库 SQLite3.Core Data 的运用: 在本节,将通过对4个文本框内容的创建.修改,退出后台,再重新回到后台,来认识这两种持久化数据的方式.效果图如下[图1]: [图1 GUI界面效果图] [本次开发环境: Xcode:7.2     iOS Simulator:iphone6S plus   By:啊左]     一.数据库SQL