每当我寻找一个IDE时(目前我正在修补Go),我都会发现很多人在推荐Vi,Emacs,Notepad ++等。
我从未在IDE之外进行任何开发;我想我已经被宠坏了。在没有IDE的情况下如何调试?您是否仅限于记录?
每当我寻找一个IDE时(目前我正在修补Go),我都会发现很多人在推荐Vi,Emacs,Notepad ++等。
我从未在IDE之外进行任何开发;我想我已经被宠坏了。在没有IDE的情况下如何调试?您是否仅限于记录?
Answers:
通过使用调试器。在大多数情况下,这也是IDE幕后的工作-它只是将体验包装在GUI中。
在Unix上,最常用的调试器之一是GNU gdb
,它已在很大程度上取代了早期的Unix调试器dbx
。
要从命令行了解调试的外观/感觉,可以查看gdb手册。
与在其他领域一样,从命令行使用调试器需要学习语法和一组命令,但具有很多灵活性和脚本性。另一方面,如果您已经习惯使用vim或emacs这样的编辑器,则可能会发现您喜欢的编辑器中有您喜欢的调试器的插件。
ipdb
比那更好;)
在编写图形驱动程序时,我使用调试器已经有好几年了。我有一台第二台计算机,它针对第一台计算机运行调试器(因为当图形驱动程序损坏时,主计算机中的屏幕将无法工作)。能够停止代码并跳到我挂上硬件的位置至关重要,这样我才能知道发生了什么。
对于纯软件问题,我发现思考问题并测试系统以了解更多有关该问题的知识比单步执行代码要有用得多。使用print语句,我可以查看在命令行或日志文件中发生的所有事情的列表,我可以查看并重构发生的事情,与调试器相比,前进和后退更容易。
通常,最棘手的错误可以通过从计算机以外的地方了解问题来解决。有时用一张纸或白板,有时我在做其他事情时答案就会显示出来。最棘手的错误可以通过仔细查看代码(例如在哪里玩Waldo)来解决。使用print语句或logging语句,所有其他似乎最简单的方法。
不同的人有不同的风格,不同的风格更适合不同的任务。打印语句不必一定要离开调试器。根据您的工作,它们甚至可以变得更好。尤其是在没有本地调试器的语言中(Go吗?)。
going backwards
。我经常有丰富的经验:“嘿- waittaminute,这是不正确的值是怎么这成为这个?”,并有去来回的输出,同时读取的代码。调试器不擅长向后。
有些人在命令行上使用gdb或插件。gdb也有独立的GUI前端,例如DDD。根据您的语言,有特定于语言的独立调试器GUI,例如适用于python的Winpdb或适用于Java的jswat。由于这些项目仅专注于调试,因此它们通常优于集成调试器。
关于IDE的另一个肮脏的小秘密是,所有这些东西都值得您花钱,让您指定自定义编辑器,因此您可以将IDE的一部分用于某些任务,但可以使用不错的编辑器进行编辑。仅启动IDE以使用其调试器的情况并不少见,特别是在您的同事都使用的情况下。
我不明白为什么不喜欢使用printf语句进行调试。曾经有一段时间,重新编译和链接程序花费的时间太长,但是今天只需要几秒钟。我发现使用cout,printf,qDebug()等类型的输出进行调试非常容易。Printf语句为您提供了程序执行所有操作的运行历史记录,您可以在事后进行分析,而在调试器中运行将使您不得不手动记住程序运行时的流程。使用printf,您可以将变量的值转换为特定单位,以十六进制,十进制等形式显示。printf语句可以列出例程和变量的名称,以及行号。您只能根据其他变量列出某些数组元素。您可以遵循间接方式。您可以非常轻松地控制输出,放入计数器,仅循环打印某些时间,在调试时添加和删除打印语句,具有不同级别的调试输出,写入文件等。要查看将程序的历史记录写入文件要容易得多。尝试记住您手动执行的所有操作,并可能不得不记下变量随时间变化的内容,以发现程序所做的事情。最后,使用printf语句,您可以将它们永久保留,以将其打开和关闭,以供将来调试。与试图记住手动记录的所有位置相比,查看程序写入文件的历史要容易得多,并且可能不得不记下变量随时间变化的内容,以便发现程序的内容。已经完成了。最后,使用printf语句,您可以将它们永久保留,以将其打开和关闭,以供将来调试。与试图记住手动记录的所有位置相比,查看程序写入文件的历史要容易得多,并且可能不得不记下变量随时间变化的内容,以便发现程序的内容。已经完成了。最后,使用printf语句,您可以将它们永久保留,以将其打开和关闭,以供将来调试。
jimwise很好地回答了这个问题,但是我想我应该补充一点,如果您选择在没有完整IDE的情况下工作,则Microsoft为Windows提供的命令行调试器称为CDB。当您下载Windows SDK时,CDB附带了其他一些工具,包括与GUI等效的WinDBG。
我通常不使用调试器,也许每两周一次,但这不是我要做的第一件事。
我工作中最重要的工具无处不在,以至于我几乎忘了提及它-堆栈跟踪。通过检查堆栈跟踪,可以解决90%以上的问题。根据您的语言,该工具并不总是很有帮助,但是如果使用一种语言将它们很好地实现,则可以节省大量时间。
我猜我发现简单问题的第二种最常见的方式是,可能是我刚刚更改的代码。我经常进行单元测试,所以我通常知道自己刚刚遇到的问题。
对于更复杂的开发和调试,我可能会添加一些调试或跟踪级别的日志语句。我认为开发问题是一个很好的指南,可以帮助我放置生产跟踪/调试日志记录信息,从而使我能够:
您并非总能方便地使用调试器。在生产中,可能无法运行调试器(哎呀,根据公司的安全程度,除日志外,可能无法访问生产计算机)。在某些语言中,连接调试器的时间太长,或者可能没有好的调试器。
如果您一直都在使用逻辑和调试/跟踪级别的日志记录进行编码,那么可能只是检查出色的日志语句(可能会增加日志级别)以找出问题而无需访问硬件的情况。
尽管我认为调试器是一个强大的工具,但不要让它们成为工具箱中唯一的工具!
没有理由不能在IDE中与独立文本编辑器一起使用调试器。我曾经使用!Zap进行编辑,使用JBuilder在另一台计算机上进行调试,以及使用地下室中的文件服务器。传统上,调试器是独立的程序,无需拖动IDE,它也可以工作。
值得注意的是,综合测试取代了调试。值得考虑的是,报告的错误是测试中的错误,而不是代码中的错误。
也有printf
。创建大量的“日志记录”并在其中进行搜索可能很有用,而不是停止每一行。如果您可以修改生产中无法修改的库类,例如-Xbootclasspath/p:
用于入侵Java库类,那么我发现这特别有用。