Class.getResource()路径起点随类位置变化,加/则从classpath根查找;ClassLoader.getResource()始终从classpath根查找且路径不能以/开头。

关键在于:Class.getResource() 的起点会随调用类的位置变化,而 ClassLoader.getResource() 始终从 classpath 根目录开始查找。
Class.getResource():路径起点取决于当前类位置
它按路径是否以 / 开头分两种行为:
- 不加 /(如
"config.properties")→ 从当前类所在包目录开始找。例如com.example.Main.class调用时,实际查找路径是classpath:/com/example/config.properties。 - 加 /(如
"/config.properties")→ 跳过包结构,直接从 classpath 根目录查,等价于ClassLoader.getResource("config.properties")。
ClassLoader.getResource():始终从 classpath 根出发
它不识别包层级,只认 classpath 下的扁平路径:
- 路径不能以 / 开头,否则返回
null。写成"/config.properties"是常见错误。 - 正确写法是
"config.properties"或"mapper/UserMapper.xml",系统自动在 classpath 根下逐级匹配。 - 适合统一管理资源位置,比如所有配置文件都放在
src/main/resources,编译后位于 classpath 根,用它最直接。
怎么选?看资源组织方式
如果资源和类紧密绑定(如 DAO 类配同名 XML 映射文件),用 Class.getResource("UserDao.xml") 更自然;如果资源是全局共享型(如日志配置、数据库连接参数),用 ClassLoader.getResource("logback.xml") 更清晰、不易受类位置变动影响。
调试小技巧:先确认当前 classpath 根在哪
加一行打印可快速定位:
-
System.out.println(YourClass.class.getResource("/"));→ 输出 classpath 根 URL -
System.out.println(YourClass.class.getResource(""));→ 输出当前类所在包路径
两者对比,就能判断资源该放哪、路径该怎么写。


















