问题描述:
在IDEA中进行结巴分词,报出如下错误:
从报错信息可以看出错误是由空指针异常引起的一个ExceptionInInitializerError错误,习惯性的没去分析就把错误往百度上一粘贴,一大堆的都是在讲静态初始化块的,看了几篇,没解决我的问题,其中个人觉得这篇文章讲静态初始化块是讲的比较好的,按我的方法没解决的朋友可以去看看:
https://blog.csdn.net/m0_38120325/article/details/89363407
网上没法解决,只好静下心来分析一下错误产生的原因:
首先可以从报错信息看出,错误是由空指针异常引起的,进入结巴分词源码对报错的地方逐个分析,最终定位在这句代码上
输出 is 看看,为空,那问题就出现在InputStream is = this.getClass().getResourceAsStream(MAIN_DICT);
在网上搜索了一下this.getClass().getResourceAsStream()的用法,原来Class.getResourceAsStream() 会指定要加载的资源路径与当前类所在包的路径一致。
例如你写了一个MyTest类在包com.test.mycode下,那么MyTest.class.getResourceAsStream(“name”)会在com.test.mycode包下查找相应的资源。
如果这个name是以 '/'开头的,那么就会从classpath的根路径下开始查找。
这下问题清晰了,我是把结巴分词的字典文件放错了地方,放在了src路径下,而IDEA的classpath路径应该是要放在resources目录下的。
具体文件和代码的位置是,代码在src/main/java目录下,资源文件在src/main/resources/目录下。
问题解决!!!
补充一下this.getClass().getResourceAsStream()的知识点:
具体文件和代码的位置是,代码在src/main/java目录下,资源文件在src/main/resources/目录下。
//拿不到资源,会从当前类的目录下去找,这个文件如果不和该类在一个目录下,就找不到。
InputStream is = this.getClass().getResourceAsStream(fileName);
// 拿到资源,会从编译后的整个classes目录下去找,maven也会把资源文件打包进classes文件夹,所以可以找到。
InputStream is = this.getClass().getResourceAsStream("/" + fileName);
//拿到资源,ClassLoader就是从整个classes文件夹找的,所以前面无需再加/。
InputStream is = this.getClass().getClassLoader().getResourceAsStream(fileName);