概述

背景
在我们开发的过程中,经常会遇到包冲突的问题,会使我们一脸懵B,为啥我明明有这个类会报ClassNotFoundException,为啥我的包的版本号是2.0,提示使用的是1.0版本云云。
原理
其实包冲突的原理非常简单,类加载器是通过全限定名(包名+类名)去加载类的,当同时有两个或者多个类的全限定名一样的时候就会出现类冲突,类加载器对相同全限定名的类是默认按名字的顺序加载的,那就有可能加载到你不要想的类。
为何会出现相同全限定名这样的情况呢,通常有两种原因,一是依赖了两个不同版本的Jar包,有可能是自己显式地依赖,但更多的可能是间接依赖引起的。什么意思呢,例如你同时依赖了A、B两个包,A包里依赖了C.1这个包,B包里依赖了C.2这个包,当你使用C包的时候,你就不确定到底是用的C.1还是C.2了。另一种原因是你自定义的包名+类名刚好跟引的包相同了,这种只能说是自己作死了,通常包名都是用不同的域名去区分的,所以没啥事不要把自己包设置成org.apache等顶级的域名。
解决方案
排查基本按以下方式走基本都能解决:
- 打印依赖树
现在构建项目基本都是用的Maven,它里面有个很强大的功能就是打印依赖树,执行mvn dependency:tree就可以把当前目录下的所有包一层层打印出来,这时你直接搜索你要排查的包名,看下它是引用自哪里。可以配合mvn dependency:resolve命令使用,这个命令可以明确地指出目前使用的包的版本。当找到了错误的版本后就需要进行排包,排包实际上就是在maven的pom文件里加上exclusion。
com.a.bclient1.0com.c.dclient
另外如果使用的是Idea开发也可以用自带的依赖树图形界面进行查看,具体方式就是在界面的右侧选“Maven Project”标签页,然后选中你想看的模块,点上面功能栏里的“Show Dependencies”即可。但是如果是项目比较复杂,包比较多就不太合适,会比较卡而且界面很乱,这里推荐一个IDEA的插件交“Maven Helper”,安装之后点击pom文件会多一个标签页,里面会清晰地显示哪些包是有冲突了。
2、打印包加载日志
在程序的启动命令上加上-verbose:class,会在启动的时候显示类加载的过程,可以通过日志搜索你的类是否被加载了,再进行进一步的分析。
总结
其实包冲突是经常会碰到的事,只要处理过几次基本就不成问题了,多总结经验即可。如果有什么说得不对的欢迎提建议。
最后
以上就是聪慧白云为你收集整理的easyexcel和poi是否有版本冲突_关于包冲突的种种的全部内容,希望文章能够帮你解决easyexcel和poi是否有版本冲突_关于包冲突的种种所遇到的程序开发问题。
如果觉得靠谱客网站的内容还不错,欢迎将靠谱客网站推荐给程序员好友。
发表评论 取消回复