如何解决NoSuchMethodError?

运行我的Java程序时出现NoSuchMethodError错误。 怎么了,我该如何解决?

如果没有更多的信息,就很难指出问题的根源,但根本原因在于,您最有可能针对缺less方法的类的不同版本编译了一个类,而不是运行它时使用的类。

查看堆栈跟踪…如果在调用库中某个对象的方法时出现exception,那么在编译和运行时很可能使用了不同版本的库。 确保你有正确的版本两个地方。

如果在所做的类实例化的对象上调用方法时出现exception,那么你的构build过程似乎是错误的。 确保在编译时更新实际运行的类文件。

我感受到你的痛苦。 你可以从一本书中学习编程,但是在使用Eclipse或者Visual Studio的时候,它会做一些简单的事情,比如添加一个库。 每个人都希望你知道如何使用它,如果你不这样做,他们downvote你的问题。 问题是,如果你不在办公室工作,或者不了解任何人可以提出这些问题,那么几乎不可能把这些东西搞清楚。 无论如何…

我有你的问题,这是我如何解决它。 以下步骤是添加库的一种工作方式。 我已经完成了前两个步骤,但是我没有通过直接从文件系统拖动“.jar”文件到我的eclipse项目中的“lib”文件夹来完成最后一步。 此外,我不得不从构buildpath和“lib”文件夹中删除以前版本的库。

如果有人知道更合适的方式添加/更新图书馆,请join。

第1步 – 添加.jar来构buildpath

在这里输入图像描述

第2步 – 关联源和javadocs(可选)

在这里输入图像描述

第3步 – 实际上拖动.jar文件到“lib”文件夹(不可选)

在这里输入图像描述

请注意,在reflection的情况下,您会得到NoSuchMethodException ,而使用非reflection代码时,会得到NoSuchMethodError 。 当面对一个对另一个时,我倾向于在非常不同的地方看。

如果您有权更改JVM参数,则添加详细输出应该允许您查看哪些类正在从哪些JAR中加载。

 java -verbose:class <other args> 

当程序运行时,JVM应该转储到标准输出信息,如:

[加载junit.framework.Assert从文件:/ C:/Program%20Files/junit3.8.2/junit.jar]

这通常是因为使用像Apache Ant这样的构build系统,当java文件比类文件更新时才编译java文件。 如果方法签名发生更改,并且类使用旧版本,则可能无法正确编译。 通常的解决办法是做一个完整的重build(通常是“ant清理”,然后“ant”)。

有时候,这也可能导致对一个版本的库进行编译,而针对不同的版本运行。

这也可以是使用reflection的结果。 如果你的代码反映了一个类,并提取一个名字的方法(例如:用Class.getDeclaredMethod("someMethodName", .....) ),那么任何时候该方法名称的变化,如在重构期间,你会需要记住将参数更新为reflection方法以匹配新的方法签名,否则getDeclaredMethod调用将抛出NoSuchMethodException

如果这是原因,那么堆栈跟踪应该显示reflection方法被调用的点,并且您只需要更新参数以匹配实际的方法签名。

根据我的经验,当unit testing私有方法/字段,并使用TestUtilities类来提取testingvalidation字段时,偶尔会出现这种情况。 (一般来说,遗留代码不是用unit testingdevise的。)

如果使用maven或其他框架,并且几乎是随机得到这个错误,请尝试“干净安装”,特别是如果您编写了对象并且知道它具有该方法。 为我工作。

如果您正在编写Web应用程序,请确保您的容器的全局库目录中以及您的应用程序中没有冲突的jar版本。 您可能不一定知道类加载器正在使用哪个jar。

例如

  • 的Tomcat /普通/ lib中
  • mywebapp / WEB-INF / lib中

这些问题是由于在相同的两个类中使用相同的对象造成的。 已使用的对象不包含新对象类所包含的新方法。

例如:

 filenotnull=/DayMoreConfig.conf 16-07-2015 05:02:10:ussdgw-1: Open TCP/IP connection to SMSC: 10.149.96.66 at 2775 16-07-2015 05:02:10:ussdgw-1: Bind request: (bindreq: (pdu: 0 9 0 [1]) 900 900 GEN 52 (addrrang: 0 0 2000) ) Exception in thread "main" java.lang.NoSuchMethodError: gateway.smpp.PDUEventListener.<init>(Lgateway/smpp/USSDClient;)V at gateway.smpp.USSDClient.bind(USSDClient.java:139) at gateway.USSDGW.initSmppConnection(USSDGW.java:274) at gateway.USSDGW.<init>(USSDGW.java:184) at com.vinaphone.app.ttn.USSDDayMore.main(USSDDayMore.java:40) -bash-3.00$ 

这些问题是由02类似的类引起的(在src中是1,在jar文件中是1,这里是gateway.jar)

这意味着各自的方法不在课堂上:

  1. 如果你正在使用jar然后反编译,并检查各个版本的jar是否有适当的类。
  2. 检查你是否从你的源码编译了适当的类。

对我来说,这是因为我改变了函数的参数types,从Object a到String a。 我可以用干净的方法来解决它,然后重新构build

当我在应用程序中更改方法签名时遇到了类似的问题。 清理和重build我的项目解决了“NoSuchMethodError”。

上面的答案解释得非常好..只是添加一件事情如果您使用的是使用eclipse使用ctrl + shift + T并input类的包结构(例如:gateway.smpp.PDUEventListener),你会发现它存在的所有jar子/项目。 从类path中删除不必要的jar或在类path中添加上面的。 现在它会select正确的一个。

我刚刚解决了这个错误,重新启动我的Eclipse并运行应用程序。 我的情况的原因可能是因为我replace我的源文件而不closures我的项目或Eclipse。 这导致了我使用的不同版本的类。

我遇到了类似的问题。

 Caused by: java.lang.NoSuchMethodError: com.abc.Employee.getEmpId()I 

最后我确定了根本原因是改变variables的数据types。

  1. Employee.java – >包含其数据types已从int更改为String的variables( EmpId )。
  2. ReportGeneration.java – >使用getter getEmpId()检索值。

我们应该通过只包含修改后的类来重新装满jar。 由于ReportGeneration.java中没有改变,我只在Jar文件中包含了Employee.class 。 我不得不在jar中包含ReportGeneration.class文件来解决这个问题。

我有同样的问题。 这也是在课堂上存在歧义时造成的。 我的程序试图调用存在于相同位置/类path中的两个JAR文件中的方法。 删除一个JAR文件或执行您的代码,以便只使用一个JAR文件。 检查您是不是使用相同的JAR或包含相同类的相同JAR的不同版本。

DISP_E_EXCEPTION [步] [] [Z-JAVA-105 Javaexceptionjava.lang.NoSuchMethodError(com.example.yourmethod)]

回答原来的问题。 根据java文档在这里 :

“NoSuchMethodError”如果应用程序尝试调用某个类的指定方法(静态或实例),并且该类不再具有该方法的定义,则抛出该exception。

通常,这个错误是由编译器捕获的; 这个错误只能在运行时发生,如果一个类的定义不兼容改变。

  1. 如果在运行时发生,请检查包含该方法的类是否在类path中。
  2. 检查是否添加了新版本的JAR,并且该方法是兼容的。

如果你的文件名不同于包含main方法的类名,那么这个错误可能是可能的。