classgemnotfoundexceptionn是什么异常

1066人阅读
JAVA集合、JVM、GC、数据结构(49)
在项目中,使用了一个JAR包,单独运行Jar包时(Java -jar jarname.jar),正常,但是将Jar包导入eclipse中,调用jar包就出现了各种错误,都是ClassNOtFoundException。开始手动将这些所引用的项目引入到项目buildpath中,后来烦的不行,因为导入一个项目,解决了一个问题。又有了一个新的类说找不到。后来回头一想,为什么CMD直接运行就可以呢?这是什么原因呢?难度是JAR包和普通的在eclipse中引用有什么不一样么?
百度了好久,最后发现了这个博客:
摘录一些要点:如下
我们这个项目需要引用其他第三方的jar包,在eclipse里面以项目jar包的形式引用了这个叫做some.jar的包,当时放在项目的lib子目录下,最后项目打包时把这个some.jar也打进来了,但是用java -jar执行这个test.jar的时候报找不到Class异常,原因就是jar引用不到放在自己内部的jar包。
那怎么办?
运行时将其加入classpath的方式行不行?就是在运行jar的同时加入classpath参数:
java -classpath some.jar -jar test.jar
这种方式是不行的,因为使用classpath指定的jar是由AppClassloader来加载,java 命令 加了-jar 参数以后,AppClassloader就只关注test.jar范围内的class了,classpath参数失效。
那该怎么引用其他的jar包呢?
方法一、使用Bootstrap Classloader来加载这些类
我们可以在运行时使用如下参数:
-Xbootclasspath:完全取代系统Java classpath.最好不用。
-Xbootclasspath/a: 在系统class加载后加载。一般用这个。
-Xbootclasspath/p: 在系统class加载前加载,注意使用,和系统类冲突就不好了.
win32 java -Xbootclasspath/a: some.some2. -jar test.jar
java -Xbootclasspath/a: some.jar:some2.jar: -jar test.jar
win32系统每个jar用分号隔开,unix系统下用冒号隔开
方法二、使用Extension Classloader来加载
你可以把需要加载的jar都扔到%JRE_HOME%/lib/ext下面,这个目录下的jar包会在Bootstrap Classloader工作完后由Extension Classloader来加载。非常方便,非常省心。
方法三、还是用AppClassloader来加载,不过不需要classpath参数了
我们在MANIFEST.MF中添加如下代码:
Class-Path: lib/some.jar
lib是和test.jar同目录的一个子目录,test.jar要引用的some.jar包就在这里面。
然后测试运行,一切正常!
如果有多个jar包需要引用的情况:
Class-Path: lib/some.jar lib/some2.jar
每个单独的jar用空格隔开就可以了。注意使用相对路径。
另:如果META-INF 下包含INDEX.LIST文件的话,可能会使Class-Path配置失效。INDEX.LIST是Jar打包工具打包时生成的索引文件,删除对运行不产生影响。
方法四、自定义Classloader来加载
这种方法是终极解决方案,基本上那些知名java应用都是那么干的,如tomcat、jboss等等。
这种方式有点复杂,需要专门开贴讨论。关于ClassLoader的原理和自定义ClassLoader可以参考这篇
以上四种方法都可以用,特别是程序运行在非常单纯的环境中时。但是,如果是运行在多任务,多应用的环境中时,最好每个应用都能相互独立,第一种和第二种方案都有可能对其他应用产生影响,因此最好就是选择第三种和第四种。
&&相关文章推荐
* 以上用户言论只代表其个人观点,不代表CSDN网站的观点或立场
访问:40317次
积分:1090
积分:1090
排名:千里之外
原创:57篇
转载:28篇
(16)(1)(3)(1)(42)(8)(20)(1)当前位置: &
求翻译:ClassNotFoundException是什么意思?
ClassNotFoundException
问题补充:
ClassNotFoundException异常
classnotfoundexception
ClassNotFoundException
ClassNotFoundException
按 tab 键以显示屏幕后,进入设置,按 esc 键进入启动显示 bootmenn menu.f12 del
我来回答:
参考资料:
* 验证码:
登录后回答可以获得积分奖励,并可以查看和管理所有的回答。 |
我要翻译和提问
请输入您需要翻译的文本!posts - 6,&
comments - 0,&
trackbacks - 0
在上篇博文中写道,通过Java的反射机制解析了指定的jar包,得到了其中的全类名,方法名,参数名,但是也许有的博友在使用时应该会发现存在一点问题。问题就是在解析简单的接口案例时可以完整的解析,但是如果解析复杂的jar包时出现ClassNotFoundException的异常。那么何为复杂的Jar包?我们平时写的小DOme,基本上依赖就JDK的jar包就可实现,但是当我们项目中引入其他的依赖jar包时,那么在利用之前写的方法通过反射去解析时,就会出现ClassNotFoundException的异常。这篇文章我们就重点来解决该问题。
我们还是以一个简单的案例来演示一下!
例如:我们要解析:HZM-payment-api-1.1.1021.jar 这个复杂的jar包。
& & & &我们知道这个jar包依赖的jar包有:activation-1.1.jar,aliyun-java-sdk-core-3.0.0.jar,aliyun-java-sdk-dm-3.0.0-rc1.jar,commons-codec-1.6.jar,commons-io-2.1.jar。。。。的一系类jar包。
   我们接下来要做的就是将这些jar包 添加到&URLClassLoader 中构建去运行环境,这样就不会出现异常了。具体代码如下:
public class jarTest {
public static void getJarName(String jarFile) throws Exception {
//通过将给定路径名字符串转换为抽象路径名来创建一个新File实例
File f = new File(jarFile);
URL url1 = f.toURI().toURL();
File f1 = new File("F:\\lib\\lib\\activation-1.1.jar");
URL url2 = f1.toURI().toURL();
File f2 = new File("F:\\lib\\lib\\aliyun-java-sdk-core-3.0.0.jar");
URL url3 = f2.toURI().toURL();
File f3 = new File("F:\\lib\\lib\\aliyun-java-sdk-dm-3.0.0-rc1.jar");
URL url4 = f3.toURI().toURL();
File f4 = new File("F:\\lib\\lib\\commons-codec-1.6.jar");
URL url5 = f4.toURI().toURL();
File f5 = new File("F:\\lib\\lib\\commons-io-2.1.jar");
URL url6 = f5.toURI().toURL();
File f6 = new File("F:\\lib\\lib\\commons-lang3-3.1.jar");
URL url7 = f6.toURI().toURL();
File f7 = new File("F:\\lib\\lib\\commons-logging-1.1.1.jar");
URL url8 = f7.toURI().toURL();
File f8 = new File("F:\\lib\\lib\\ELP-common-branch-1.95.jar");
URL url9 = f8.toURI().toURL();
File f9 = new File("F:\\lib\\lib\\fastjson-1.1.43.jar");
URL url10 = f9.toURI().toURL();
File f10 = new File("F:\\lib\\lib\\httpclient-4.2.1.jar");
URL url11 = f10.toURI().toURL();
File f11 = new File("F:\\lib\\lib\\httpcore-4.2.1.jar");
URL url12 = f11.toURI().toURL();
File f12 = new File("F:\\lib\\lib\\jaxrs-api-3.0.7.Final.jar");
URL url13 = f12.toURI().toURL();
File f13 = new File("F:\\lib\\lib\\jboss-annotations-api_1.1_spec-1.0.1.Final.jar");
URL url14 = f13.toURI().toURL();
File f14 = new File("F:\\lib\\lib\\jcip-annotations-1.0.jar");
URL url15 = f14.toURI().toURL();
File f15 = new File("F:\\lib\\lib\\jcl-over-slf4j-1.7.10.jar");
URL url16 = f15.toURI().toURL();
File f16 = new File("F:\\lib\\lib\\log4j-over-slf4j-1.7.10.jar");
URL url17 = f16.toURI().toURL();
File f17 = new File("F:\\lib\\lib\\logback-classic-1.1.2.jar");
URL url18 = f17.toURI().toURL();
File f18 = new File("F:\\lib\\lib\\resteasy-jaxrs-3.0.7.Final.jar");
URL url19 = f18.toURI().toURL();
File f19 = new File("F:\\lib\\lib\\slf4j-api-1.7.10.jar");
URL url20 = f19.toURI().toURL();
File f20 = new File("F:\\lib\\lib\\taobao-sdk-java-auto-.jar");
URL url21 = f20.toURI().toURL();
File f21 = new File("F:\\lib\\lib\\HZM-common-1.0.jar");
URL url22 = f21.toURI().toURL();
URLClassLoader myClassLoader = new URLClassLoader(new URL[]{url1,url2,url3,url4,
url5,url6,url7,url8,url9,url10,url11,url12,url13,url4,url15,url16,url17,
url18,url19,url20,url21,url22},Thread.currentThread().getContextClassLoader());
//通过jarFile和JarEntry得到所有的类
JarFile jar = new JarFile(jarFile);
System.out.println("解析的文件名为:"+jarFile);
//返回zip文件条目的枚举
Enumeration&JarEntry& enumFiles = jar.entries();
//测试此枚举是否包含更多的元素
while(enumFiles.hasMoreElements()){
entry = (JarEntry)enumFiles.nextElement();
if(entry.getName().indexOf("META-INF")&0){
String classFullName = entry.getName();
if(!classFullName.endsWith(".class")){
classFullName = classFullName.substring(0,classFullName.length()-1);
//去掉后缀.class
String className = classFullName.substring(0,classFullName.length()-6).replace("/", ".");
Class&?& myclass = myClassLoader.loadClass(className);
// Class&?& myclass=myClassLoader.findClass(className);
//判断是否为接口
只解析接口
isInterface =myclass.isInterface();
if(isInterface){
//打印类名
System.out.println("*****************************");
System.out.println("全类名:" + className);
System.out.println(isInterface);
//得到类中包含的属性
Method[] methods = myclass.getMethods();
for (Method method : methods) {
String methodName = method.getName();
System.out.println("方法名称:" + methodName);
Class&?&[] parameterTypes = method.getParameterTypes();
for (Class&?& clas : parameterTypes) {
// String parameterName = clas.getName();
String parameterName = clas.getSimpleName();
System.out.println("参数类型:" + parameterName);
System.out.println("==========================");
} catch(IOException e){
e.printStackTrace();
public static void main(String[] args) throws Exception {
//jar包所在路径
getJarName("F:\\lib\\lib\\HZM-payment-api-1.1.1021.jar");
  可能会有很多博友会觉得手动添加jar包会很麻烦。接下来我将写一篇通过文件上传来上传jar包,避免手动输入繁琐
阅读(...) 评论()NoClassDefFoundError与ClassNotFoundException的区别 -
- ITeye博客
博客分类:
相同点:
1、NoClassDefFoundError和ClassNotFoundException都是类运行时出错。
2、都和classpath有关。
不同点:
1、ClassNotFoundException继承java.lang.Exception,是一种受检异常(checked exception),需要显式地使用try/catch来进行处理。通常需要确保需要的类已经在classpath上了。
--------------------------------
而NoClassDefFoundError继承java.lang.LinkageError,是一种错误(Error)。
2、ClassNotFoundException发生在类加载器在classpath上找不到相关类的时候,通常会使用Class.forName()或ClassLoader.loadClass()或ClassLoader.findSystemClass()。
有时我们会主观地认为类已经在classpath上了,但其实不是,例如jar包中的manifest文件的优先级比当前classpath或-cp选项指定的classpath的优先级都要高,就有可能发生ClassNotFoundException。
还有一种也会发生ClassNotFoundException的场景就是使用两个类加载器,一个类加载器尝试着访问已经被另一个类加载器加载的类也会导致ClassNotFoundException。
--------------------------------
而NoClassDefFoundError相对来说更难诊断出原因。
有时会发生在运行期依赖的类变更了或被删除了,例如下面这个例子,Test类中依赖Test1类,在编译时Test1存在,
编译成功后,删除Test1.class文件,再运行Test类时,就会报错:
Exception in thread "main" java.lang.NoClassDefFoundError: Test
at Test1.main(Test1.java:5)
Caused by: java.lang.ClassNotFoundException: Test
at java.net.URLClassLoader$1.run(Unknown Source)
at java.net.URLClassLoader$1.run(Unknown Source)
at java.security.AccessController.doPrivileged(Native Method)
at java.net.URLClassLoader.findClass(Unknown Source)
at java.lang.ClassLoader.loadClass(Unknown Source)
at sun.misc.Launcher$AppClassLoader.loadClass(Unknown Source)
at java.lang.ClassLoader.loadClass(Unknown Source)
... 1 more
NoClassDefFoundError还可能发生在类的静态代码块中抛出了异常,例如:
配置文件中没有PROM_REDIS_MAXACTIVE项,是null,导致类的静态代码块出错,从而引起NoClassDefFoundError:
java.lang.NoClassDefFoundError: com.jag.StringSingleCacheClient (initialization failure)
at java.lang.J9VMInternals.initialize(J9VMInternals.java:140)
浏览: 9236 次
来自: 上海
1,一致性hash主要通过环形hash满足单调性,通过虚拟节点 ...
dieslrae 写道数组的生产和消费怎么可以分离,每一次消费 ...
数组的生产和消费怎么可以分离,每一次消费都涉及到数组元素的移动 ...
yunchow 写道以下java代码会引起活锁:在a线程里:b ...
死锁是两个线程同时在请求对方占有的资源;活锁是线程对任务的处理 ...项目集成Maven后JUnit报ClassNotFoundException错误原因及解决方法 - WEB开发工具 - 编程入门网
项目集成Maven后JUnit报ClassNotFoundException错误原因及解决方法
前提:原有项目一切运行正常,单元测试正常执行。
项目开始使用Maven管理,结果发现原有的JUnit测试无法执行,类无法找到(java.lang.ClassNotFoundException)。无论如何修改Maven配置,报错依然。
分析原因:
MyEclipse之所以能识别项目,是根据.project文件解析;而项目的目录结构则是在.classpath文件中定义。MyEclipse的JUnit插件也是根据以上文件来查找源代码和class文件的存放目录。项目集成Maven后,通过执行maven命令,则class文件生成目录由pom.xml文件指定。
而Maven默认使用的工程目录结构和MyEclipse中的默认目录结构不同,此时,当pom.xml文件中指定的目录和.classpath文件指定的目录不同时,就会报上文中提到的错误。
因此,项目集成Maven时,执行JUnit测试时需要注意的地方如下:
pom.xml文件中的如下配置
应该和.classpath文件中的如下配置相对应。
如此配置之后,JUnit可正确执行,而又不影响Maven的打包、发布等功能。}

我要回帖

更多关于 classnotfound 的文章

更多推荐

版权声明:文章内容来源于网络,版权归原作者所有,如有侵权请点击这里与我们联系,我们将及时删除。

点击添加站长微信