岁月联盟 - 技术社区 - BBS.SYUE.COM's Archiver

huxinisme 发表于 2007-2-28 23:19

程序调试阶段常见的两个异常

ClassNotFoundException和NoClassDefFoundErr异常

在读这篇文章之前,你最好了解一下Java的Exception机制。




    也许你在开发的过程中经常地见到ClassNotFoundException和NoClassDefFoundErr这两个异常,每每看到之后,都会一概而论的是类没有找到,但有些时候见到他们的时候又有些疑惑(至少我是这样),为什么Java要用两个异常来表示类定义没有找到呢?他们之间有什么区别呢?

    正巧今天我又碰到了这个问题,顺便仔细研究了一下这两个异常的区别。

    首先:

ClassNotFoundException直接继承与Exception,它是一个checked的异常。
NoClassDefFoundErr 继承自Error->LinkageError ,它是一个unchecked的异常。

    下面让我们看一下两个异常在API文档中的说明。

    ClassNotFoundException:
    当应用尝试用字符串名称通过下面的方法装载一个类,这个类的定义却没有找到时会抛出的异常。
■Class.forName
■ClassLoader.findSystemClass
■ClassLoader.loadClass

    NoClassDefFoundErr:

    当JVM或者ClassLoader实例尝试装载一个类的定义(这通常是一个方法调用或者new表达式创建一个实例过程的一部分),而这个类定义并没有找到时所抛出的错误。

    当编译的时候可以找到这个类的定义,但是以后这个类不再存在。

    这比较显而易见了吧,读好文档是很重要的事情。这里我就说一下我对这两个类的区别的理解。

    ClassNotFoundException异常只出现在你的应用程序主动的装载类的过程中,这个异常很多时候出现在,我们的应用框架在初始化、或者运行中动态装载已配置的类的过程中。这种情况下,我们应该首先检查我们的配置或者参数是否错误,是否企图装载一个并不存在的类,如果配置没有错误,我们就应该查看Classpath是否配置错误而导致ClassLoader无法找到这个类,也应该检查要装载的类是否在一个jar包中,而我们在引入这个jar包的过程中是否有遗漏或错误(这里jar包的版本也是一个需要格外注意的问题,很多时候混乱的jar包版本会造成太多的麻烦)。

    NoClassDefFoundErr异常一般出现在我们编译环境和运行环境不一致的情况下,就是说我们有可能在编译过后更改了Classpath或者jar包所以导致在运行的过程中JVM或者ClassLoader无法找到这个类的定义(我曾经在编译后作了一次jar包的清理,然后应用就送给了我一个这样的礼物)。

    我们经常用SDK开发应用,开发的过程中要引入很多jar包,有些SDK也会设定自己的Classpath。编译过程结束后在运行的过程中就要将已开发的应用和所有引入的jar包拷贝到应用服务器的相应目录下才可以运行,而应用服务器使用的Classpath也很有可能与SDK的不同,在这个过程中就有很大的几率造成双方环境不一致。所以很多开发者就会遇到在SDK中可以编译,运行也没有问题,但是同样的程序放到应用服务器上就出现NoClassDefFoundErr这个异常这种情况,这是让初学者很头疼的一个问题。

    以上就是我对这两个异常的一点个人理解,希望对各位开发者有所帮助,可以让各位开发者在以后的开发过程中能够更快的找到问题所在。祝开发顺利!

页: [1]

Powered by Discuz! Archiver 7.0.0  © 2001-2009 Comsenz Inc.