赞
踩
说明 | 快捷键 |
---|---|
复制代码-copy | ctrl + c |
粘贴-paste | ctrl + v |
剪切-cut | ctrl + x |
撤销-undo | ctrl + z |
反撤销-redo | ctrl + shift + z |
保存-save all | ctrl + s |
全选-select all | ctrl + a |
说明 | 快捷键 |
---|---|
智能提示-edit | alt + enter |
提示代码模板-insert live template | ctrl+j |
使用xx块环绕-surround with … | ctrl+alt+t |
调出生成getter/setter/构造器等结构-generate … | alt+insert |
自动生成返回值变量-introduce variable … | ctrl+alt+v |
复制指定行的代码-duplicate line or selection | ctrl+d |
删除指定行的代码-delete line | ctrl+y |
切换到下一行代码空位-start new line | shift + enter |
切换到上一行代码空位-start new line before current | ctrl +alt+ enter |
向上移动代码-move statement up | ctrl+shift+↑ |
向下移动代码-move statement down | ctrl+shift+↓ |
向上移动一行-move line up | alt+shift+↑ |
向下移动一行-move line down | alt+shift+↓ |
方法的形参列表提醒-parameter info | ctrl+p |
说明 | 快捷键 |
---|---|
批量修改指定的变量名、方法名、类名等-rename | shift+f6 |
抽取代码重构方法-extract method … | ctrl+alt+m |
重写父类的方法-override methods … | ctrl+o |
实现接口的方法-implements methods … | ctrl+i |
选中的结构的大小写的切换-toggle case | ctrl+shift+u |
批量导包-optimize imports | ctrl+alt+o |
说明 | 快捷键 |
---|---|
如何查看源码-go to class… | ctrl + 选中指定的结构 或 ctrl+n |
显示当前类结构,支持搜索指定的方法、属性等-file structure | ctrl+f12 |
退回到前一个编辑的页面-back | ctrl+alt+← |
进入到下一个编辑的页面-forward | ctrl+alt+→ |
打开的类文件之间切换-select previous/next tab | alt+←/→ |
光标选中指定的类,查看继承树结构-Type Hierarchy | ctrl+h |
查看方法文档-quick documentation | ctrl+q |
类的UML关系图-show uml popup | ctrl+alt+u |
定位某行-go to line/column | ctrl+g |
回溯变量或方法的来源-go to implementation(s) | ctrl+alt+b |
折叠方法实现-collapse all | ctrl+shift+ - |
展开方法实现-expand all | ctrl+shift+ + |
说明 | 快捷键 |
---|---|
查找指定的结构 | ctlr+f |
快速查找:选中的Word快速定位到下一个-find next | ctrl+l |
查找与替换-replace | ctrl+r |
直接定位到当前行的首位-move caret to line start | home |
直接定位到当前行的末位 -move caret to line end | end |
查询当前元素在当前文件中的引用,然后按 F3 可以选择 | ctrl+f7 |
全项目搜索文本-find in path … | ctrl+shift+f |
关闭当前窗口-close | ctrl+f4 |
说明 | 快捷键 |
---|---|
格式化代码-reformat code | ctrl+alt+l |
使用单行注释-comment with line comment | ctrl + / |
使用/取消多行注释-comment with block comment | ctrl + shift + / |
选中数行,整体往后移动-tab | tab |
选中数行,整体往前移动-prev tab | shift + tab |
说明 | 快捷键 |
---|---|
单步调试(不进入函数内部)- step over | F8 |
单步调试(进入函数内部)- step into | F7 |
强制单步调试(进入函数内部) - force step into | alt+shift+f7 |
选择要进入的函数 - smart step into | shift + F7 |
跳出函数 - step out | shift + F8 |
运行到断点 - run to cursor | alt + F9 |
继续执行,进入下一个断点或执行完程序 - resume program | F9 |
停止 - stop | Ctrl+F2 |
查看断点 - view breakpoints | Ctrl+Shift+F8 |
关闭 - close | Ctrl+F4 |
苹果电脑或者是用惯Eclipse快捷的,可以选择其他快捷键插件。
编好的程序在执行过程中如果出现错误,该如何查找或定位错误呢?简单的代码直接就可以看出来,但如果代码比较复杂,就需要借助程序调试工具(Debug)来查找错误了。
运行编写好的程序时,可能出现的几种情况:
> 情况1:没有任何bug,程序执行正确!
====================如果出现如下的三种情况,都又必要使用debug=============================
> 情况2:运行以后,出现了错误或异常信息。但是通过日志文件或控制台,显示了异常信息的位置。
> 情况3:运行以后,得到了结果,但是结果不是我们想要的。
> 情况4:运行以后,得到了结果,结果大概率是我们想要的。但是多次运行的话,可能会出现不是我们想要的情况。
比如:多线程情况下,处理线程安全问题。
Debug(调试)程序步骤如下:
1、添加断点
2、启动调试
3、单步执行
4、观察变量和执行流程,找到并解决问题
在源代码文件中,在想要设置断点的代码行的前面的标记行处,单击鼠标左键就可以设置断点,在相同位置再次单击即可取消断点。
IDEA提供多种方式来启动程序(Launch)的调试,分别是通过菜单(Run –> Debug)、图标(“绿色臭虫”)等等。
或
【解释】
:Step Over(F8):进入下一步,如果当前行断点是调用一个方法,则不进入当前方法体内。
:Step Into(F7):进入下一步,如果当前行断点是调用一个自定义方法,则进入该方法体内。
:Force Step Into(Alt +Shift + F7):进入下一步,如果当前行断点是调用一个核心类库方法,则进入该方法体内。(强制进入)
:Step Out(Shift + F8):跳出当前方法体。
:Run to Cursor(Alt + F9):直接跳到光标处继续调试。
:Resume Program(F9):恢复程序运行,但如果该断点下面代码还有断点则停在下一个断点上。(跳到下一个断点)
:Stop(Ctrl + F2):结束调试。
:View Breakpoints(Ctrl + Shift + F8):查看所有断点。
:Mute Breakpoints:使得当前代码后面所有的断点失效, 一下执行到底。
:重新运行。
:显示执行点,若在此行代码中,进入了其中一个函数查看,想要再返回刚才调试的这一行代码,可以点这个按钮。
说明:在Debug过程中,可以动态的下断点。
【案例1】
package com.atguigu.debug; /** * ClassName: Debug01 * Package: com.atguigu.debug * Description: 演示1:行断点 & 测试debug各个常见操作按钮 */ public class Debug01 { public static void main(String[] args) { //1. int m = 10; int n = 20; System.out.println("m = " + m + ",n = " + n); swap(m, n); System.out.println("m = " + m + ",n = " + n); //2. // int[] arr = new int[] {1,2,3,4,5}; // System.out.println(arr);//地址值 // char[] arr1 = new char[] {'a','b','c'}; // System.out.println(arr1);//abc } public static void swap(int m,int n){ int temp = m; m = n; n = temp; } }
此时得到的不是想要的结果:
此时就可以通过调试来发现问题。
打断点在哪里打呢?一般在你怀疑出错的代码的前面一行打上断点。
比如现在怀疑swap()
方法有问题,就可以将断点打到上面一行,如下:
断点是红色的,用鼠标左键在左边点一下即可。
接下来调试一下,点击“Debug”:
然后代码就会执行到首次添加断点的位置,此时这一行代码还没有执行。如下:
然后执行下一步:
此时想进入swap()方法内部,点击第二个按钮(因为这里的swap方法是自己写的,若是系统函数比如print函数,就需要第三个按钮强制进入):
然后一步一步执行:
此时swap()执行完毕,可以跳出来,不用继续执行后续代码:
【案例2】
package com.atguigu.debug; /** * ClassName: Debug01 * Package: com.atguigu.debug * Description: 演示1:行断点 & 测试debug各个常见操作按钮 */ public class Debug01 { public static void main(String[] args) { //1. // int m = 10; // int n = 20; // System.out.println("m = " + m + ",n = " + n); // swap(m, n); // System.out.println("m = " + m + ",n = " + n); //2. int[] arr = new int[] {1,2,3,4,5}; System.out.println(arr);//地址值 char[] arr1 = new char[] {'a','b','c'}; System.out.println(arr1);//abc } public static void swap(int m,int n){ int temp = m; m = n; n = temp; } }
打断点进行调试:
强制进入print函数:
再次强制进入valueOf:
可以看到,直接调用toString:
这里可以跳出方法:
对于第二个也可以使用同样的方法进入调试:
【案例1】
package yuyi03.Debug; /** * ClassName: Debug02 * Package: com.atguigu.debug * Description: 演示2: 方法断点 * @Version 1.0 */ public class Debug02 { public static void main(String[] args) { //1. Son instance = new Son(); instance.test(); // //2.类的多态性 // Father instance1 = new Son(); // instance1.test(); // // //3.接口的多态性 // Consumer con = new ConsumerImpl(); // con.accept("atguigu"); //4. // HashMap map = new HashMap(); // map.put("Tom",12); // map.put("Jerry",11); // map.put("Tony",20); } } class Father{ public void test(){ System.out.println("Father : test1"); System.out.println("Father : test2"); } } class Son extends Father{ @Override public void test(){ System.out.println("Son : test1"); System.out.println("Son : test2"); } } interface Consumer{ void accept(String str); } class ConsumerImpl implements Consumer{ @Override public void accept(String str) { System.out.println("ConsumerImple:" + str); } }
方法断点,比如在这个方法左边打上断点,可以看到是一个菱形:
右键点击菱形,可以看到它指明了在进入方法的时候,会停留一下。
然后开始调试:
可以看到它直接停留在方法这里了:
这是因为上面调用这个方法了:
一调用这个方法,它就停留在这里了。
给方法声明这里加断点,就是看这个方法什么时候调用,调用的时候就重点看方法的执行。
【案例2】
package yuyi03.Debug; /** * ClassName: Debug02 * Package: com.atguigu.debug * Description: 演示2: 方法断点 * @Version 1.0 */ public class Debug02 { public static void main(String[] args) { //1. // Son instance = new Son(); // instance.test(); //2.类的多态性 Father instance1 = new Son(); instance1.test(); //3.接口的多态性 Consumer con = new ConsumerImpl(); con.accept("atguigu"); //4. // HashMap map = new HashMap(); // map.put("Tom",12); // map.put("Jerry",11); // map.put("Tony",20); } } class Father{ public void test(){ System.out.println("Father : test1"); System.out.println("Father : test2"); } } class Son extends Father{ @Override public void test(){ System.out.println("Son : test1"); System.out.println("Son : test2"); } } interface Consumer{ void accept(String str); } class ConsumerImpl implements Consumer{ @Override public void accept(String str) { System.out.println("ConsumerImple:" + str); } }
在方法声明处打上断点:
编写的时候,会认为调用的是父类/接口中的方法,实际执行的时候是子类/实现类中的方法:
那么此时调试会做停留吗?
可以发现其实停留了,而且停留在了子类Son这里,如下:
刚才说了,实际运行的时候,执行的是子类重写父类的方法。
所以这里是真正运行了。
为什么在父类那里打的断点,跳到了子类这里?这是因为子类将父类的方法给覆盖了。
接下来看一下“下一个可能有断点的位置”:
可以看到跳到了Consumer实现类的地方:
通过Debug可以看到真正执行的是哪一个类的方法
现在可以查看一下当前代码中都有哪些位置有断点:
【案例1】
package com.atguigu.debug; /** * ClassName: Debug03 * Package: com.atguigu.debug * Description: 演示3:字段断点 * @Version 1.0 */ public class Debug03 { public static void main(String[] args) { Person p1 = new Person(3); System.out.println(p1.toString()); } } class Person{ private int id = 1; //显示赋值 private String name; private int age; public Person() { } { id = 2; //代码块赋值 } public Person(int id) { this.id = id; //构造器赋值 } public Person(int id, String name, int age) { this.id = id; this.name = name; this.age = age; } public int getId() { return id; } public void setId(int id) { this.id = id; } public String getName() { return name; } public void setName(String name) { this.name = name; } public int getAge() { return age; } public void setAge(int age) { this.age = age; } @Override public String toString() { return "Person{" + "id=" + id + ", name='" + name + '\'' + ", age=" + age + '}'; } }
在属性前面加断点是一个小眼睛,比如:
右键可以看到,在修改当前属性的时候,会停留一下(相当于就是看一下哪些位置修改了):
现在我们调试一下,凡是修改了属性的位置都会停下来。
可以看到这里显式赋值算修改了,因为默认值是0。
此时p1对象还没有创建,调用构造器之前先是显示赋值了,所以this里面的id是0,如下:
点击这里,找到下一个断点位置代码块:
此时this里面的id变为了1,说明显示赋值已经执行了。
再下一个位置就是构造器了,如下:
一共就这三个位置修改了id,再次寻找断点位置就会结束。
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。