相信还有很多人和我一样,当调试时想要查看某个参数的值的时候,会在代码中用log打印,然后重新运行。当log多了后,常常容易搞乱,而且总是重新运行、调试完删除log都很费事。这里介绍通过lldb来增加调试效率。
调试中我们经常需要打断点,当程序运行到断点时,程序会暂停,此时控制台会出现
(lldb)
这就表示我们可以在控制台里输入lldb指令进行操作(Xcode5之后lldb取代gdb,成为了Xcode工程中默认的调试器
),lldb指令是区分大小写的,且能提供代码输入提示。
一、基本的lldb指令
1. p命令
p命令是“expression --”的简写,也可写为“print”。使用方法为“p <表达式>”,如果p后的参数为基本数据类型,则直接打印基本数据类型的值,如果参数为对象类型,则会打印对象的地址,如果对象是NSString类型,则还会打印字符串的内容。除此之外,一些常用的表达式也都可以作为参数如定义了整型a,则可以使用“p ++a”等。下图显示具体操作。
p指令的使用
1.当显示的过程中我们看到每次的执行结果的左边都以相同的格式显示,先是数据类型,然后是一个$+数字的变量名,这里的$1,$2的变量都是原数据的引用,我们可以使用原数据的名称,也可以直接使用"$N"的形式使用对象,效果是一样的。
2.这里需要注意的是,因为指令及结果中要么用到的是变量本事,要么变量的引用,所以当我们调用了“++a”之后,程序中原来的a的也会跟着改变。不过这些指令操作都是临时的,并不会改变代码。下次运行时这些指令并不会运行,a的输出结果还是10。
2. po指令
po命令(是“expression -O --”指令的简写,可以理解为print object)。这是在iOS中用到的最多的指令,因为iOS我们遇到的基本都是对象类型,po指令的作用是打印对象的description描述。类似于在NSLog中使用%@打印对象类型。po指令当然也可以使用基本数据类型和一般的表达式,效果同p指令,只是显示格式不同。(po指令的操作对象也是原参数的引用,因此也会改变原来的值)。
po指令的使用
1.在执行过程中我们看到当参数为基本数据类型与NSString类型时,只打印了他们的值。除此之外po指令的参数还可以是地址图中使用了“po 0x7fae3bc0b9f0”(不过我也遇到过这条指令把地址当做了一个16进制的数,然后输出的结果为转为10进制之后的值的情况o(╯□╰)o), 当然,如果po后的16进制数不是12位时,输出结果一定是一个10进制数。
2.其次,在po指令中,我们也可以获取在当前断点处的self指针,并调用点语法。除此之外,强制类型转换,判断语句等等表达式都是可以使用的。
3. help指令
这里只介绍以上两个最常用的指令,其他指令我们可以通过help指令在需要时自行查找。通常在终端或命令行执行的语句都会有的help指令,通过help指令我们查看指令列表及指令的介绍。以字母顺序排列。其次还可以使用“help <指令名>”的格式查看对应指令的用法及可以使用的参数。例如“help p”。
二、与断点结合
当我们通过断点调试时,可以为断点增加触发的判断条件,断点内容运行完后自动继续执行等达到很多在运行时自动执行一些调试操作的目的。而上述的lldb指令我们都是在断点处停下来后,等我们人工操作完才能继续运行程序。二者是可以结合的。如下图:
运行时增加打印及取消
当我们进入断点编辑界面时,在Action中选择Debugger Command。然后可以在下面增加lldb的一些指令,只不过这里没有自动提示输入功能,我们可以在代码中先敲完后复制进来。指令可以执行多条,执行的指令与在命令行下相同。如果我们把Automaticlly continue after evaluating actions勾选上后,当程序运行到断定是并不会停下。能实现和NSLog同样的功能,同时能在程序运行时就能实现打印的增加修改及删除,相比NSLog能方便很多。
更多关于lldb的内容可以查看http://lldb.llvm.org