java編譯,採用增量更新的時候報NoSuchMethodError錯誤
阿新 • • 發佈:2018-12-10
java.lang.NoSuchMethodError:com.lfsenior.cn.TestDemo.getParam(Ljava/lang/String;)Ljava/util/Map; com.lfsenior.TestWeb.doGet(TestWeb.java:19)javax.servlet.http.HttpServlet.service(HttpServlet.java:622) javax.servlet.http.HttpServlet.service(HttpServlet.java:729) org.apache.tomcat.websocket.server.WsFilter.doFilter(WsFilter.java:52)
在通過javap -c -verbose TestWeb.class >> demo3.java 命令反編譯的時候我們可以看到如下結果
當採用增量更新的方式的時候,如果我們更改了某個類的引數型別,即使更改的時候採用了多型,即使用父類替換子類的方式,依舊會出現問題,因為當這個方法被在其他地方使用並編譯的時候,使用的引數型別依舊是子類,所有就會報NoSuchMethodError的錯誤。解決辦法,將所有應該改方法的類重新編譯後更新即可
測試程式碼地址:
https://gitee.com/lfsenior/STU/tree/master/testdemo
https://gitee.com/lfsenior/STU/tree/master/testdemoweb
反編譯原始碼:
Classfile /Users/lisongli/Desktop/dlpan/stuproject/stu/testdemoweb/target/classes/com/lfsenior/TestWeb.class Last modified Oct 8, 2018; size 1034 bytes MD5 checksum f5f61c26872770e358bbdd5ffdbe59e5 Compiled from "TestWeb.java" public class com.lfsenior.TestWeb extends javax.servlet.http.HttpServlet minor version: 0 major version: 51 flags: ACC_PUBLIC, ACC_SUPER Constant pool: #1 = Methodref #8.#29 // javax/servlet/http/HttpServlet."<init>":()V #2 = InterfaceMethodref #30.#31 // javax/servlet/http/HttpServletResponse.getWriter:()Ljava/io/PrintWriter; #3 = String #32 // test #4 = Methodref #33.#34 // com/lfsenior/cn/TestDemo.getParam:(Ljava/lang/Object;)Ljava/util/Map; #5 = Methodref #35.#36 // java/lang/Object.toString:()Ljava/lang/String; #6 = Methodref #37.#38 // java/io/PrintWriter.write:(Ljava/lang/String;)V #7 = Class #39 // com/lfsenior/TestWeb #8 = Class #40 // javax/servlet/http/HttpServlet #9 = Utf8 <init> #10 = Utf8 ()V #11 = Utf8 Code #12 = Utf8 LineNumberTable #13 = Utf8 LocalVariableTable #14 = Utf8 this #15 = Utf8 Lcom/lfsenior/TestWeb; #16 = Utf8 doGet #17 = Utf8 (Ljavax/servlet/http/HttpServletRequest;Ljavax/servlet/http/HttpServletResponse;)V #18 = Utf8 req #19 = Utf8 Ljavax/servlet/http/HttpServletRequest; #20 = Utf8 resp #21 = Utf8 Ljavax/servlet/http/HttpServletResponse; #22 = Utf8 writer #23 = Utf8 Ljava/io/PrintWriter; #24 = Utf8 Exceptions #25 = Class #41 // javax/servlet/ServletException #26 = Class #42 // java/io/IOException #27 = Utf8 SourceFile #28 = Utf8 TestWeb.java #29 = NameAndType #9:#10 // "<init>":()V #30 = Class #43 // javax/servlet/http/HttpServletResponse #31 = NameAndType #44:#45 // getWriter:()Ljava/io/PrintWriter; #32 = Utf8 test #33 = Class #46 // com/lfsenior/cn/TestDemo #34 = NameAndType #47:#48 // getParam:(Ljava/lang/Object;)Ljava/util/Map; #35 = Class #49 // java/lang/Object #36 = NameAndType #50:#51 // toString:()Ljava/lang/String; #37 = Class #52 // java/io/PrintWriter #38 = NameAndType #53:#54 // write:(Ljava/lang/String;)V #39 = Utf8 com/lfsenior/TestWeb #40 = Utf8 javax/servlet/http/HttpServlet #41 = Utf8 javax/servlet/ServletException #42 = Utf8 java/io/IOException #43 = Utf8 javax/servlet/http/HttpServletResponse #44 = Utf8 getWriter #45 = Utf8 ()Ljava/io/PrintWriter; #46 = Utf8 com/lfsenior/cn/TestDemo #47 = Utf8 getParam #48 = Utf8 (Ljava/lang/Object;)Ljava/util/Map; #49 = Utf8 java/lang/Object #50 = Utf8 toString #51 = Utf8 ()Ljava/lang/String; #52 = Utf8 java/io/PrintWriter #53 = Utf8 write #54 = Utf8 (Ljava/lang/String;)V { public com.lfsenior.TestWeb(); descriptor: ()V flags: ACC_PUBLIC Code: stack=1, locals=1, args_size=1 0: aload_0 1: invokespecial #1 // Method javax/servlet/http/HttpServlet."<init>":()V 4: return LineNumberTable: line 15: 0 LocalVariableTable: Start Length Slot Name Signature 0 5 0 this Lcom/lfsenior/TestWeb; protected void doGet(javax.servlet.http.HttpServletRequest, javax.servlet.http.HttpServletResponse) throws javax.servlet.ServletException, java.io.IOException; descriptor: (Ljavax/servlet/http/HttpServletRequest;Ljavax/servlet/http/HttpServletResponse;)V flags: ACC_PROTECTED Code: stack=2, locals=4, args_size=3 0: aload_2 1: invokeinterface #2, 1 // InterfaceMethod javax/servlet/http/HttpServletResponse.getWriter:()Ljava/io/PrintWriter; 6: astore_3 7: aload_3 8: ldc #3 // String test 10: invokestatic #4 // Method com/lfsenior/cn/TestDemo.getParam:(Ljava/lang/Object;)Ljava/util/Map; 13: invokevirtual #5 // Method java/lang/Object.toString:()Ljava/lang/String; 16: invokevirtual #6 // Method java/io/PrintWriter.write:(Ljava/lang/String;)V 19: return LineNumberTable: line 18: 0 line 19: 7 line 20: 19 LocalVariableTable: Start Length Slot Name Signature 0 20 0 this Lcom/lfsenior/TestWeb; 0 20 1 req Ljavax/servlet/http/HttpServletRequest; 0 20 2 resp Ljavax/servlet/http/HttpServletResponse; 7 13 3 writer Ljava/io/PrintWriter; Exceptions: throws javax.servlet.ServletException, java.io.IOException } SourceFile: "TestWeb.java"