加载中

Java

文章分类

浏览该分类下的所有文章

237 篇文章 20

IDEA 2022.2版本新特性

IDEA 2022.2 引入远程开发模式,后端部署在服务器,前端 thin client 本地使用,通过 SSH 分担重任务提升流畅度;全面支持 Spring 6 与 Spring Boot 3,包括 @AutoConfiguration、@ConfigurationProperties 等新特性;新增 ⌃⇧. /⌃⇧, 快捷键全局调节编辑器字体大小;JSON、YAML、properties 中的 http/https 链接可直接点击打开或生成 HTTP 请求;实验性 GraalVM 原生调试器支持调试本地镜像;Bean Validation 注解的消息属性支持引用与折叠;其他改进包括 Groovy 集成查询、升级内置 Kubernetes/Docker、运行当前文件无需配置、导入受信任 SSL 证书、HTTP 客户端优化、JBR11→JBR17、代码检查与补全增强等。

解决SpringBoot打成jar包无法加载resources下文件的问题

SpringBoot 打成 jar 包后,Linux 环境下常出现无法读取 classpath 中 resources 目录下文件(如 application.yml、ip2region.db)的情况。文章给出一种通用解决方案:使用 Spring 的 `PathMatchingResourcePatternResolver` 通过通配符获取资源数组,取首个 `Resource` 后获取 `InputStream`,再借助 Apache Commons‑IO 的 `FileUtils.copyInputStreamToFile` 将流写入本地文件(如 `ip2region.db`),完成后关闭流。示例代码演示了所需的核心导入包(`org.springframework.core.io.*`、`org.apache.commons.io.FileUtils`)以及完整实现步骤,确保 jar 包运行时能够正确加载并使用 resources 里的文件。

StringUtils部分API的用法与区别

本文系统演示了 Apache Commons‑Lang3 中 `StringUtils` 常用判断 API 的使用差异。通过示例代码说明:`isEmpty` 只判断 null 与空串,不把空格算作空;`isAnyEmpty` 任意参数为 null/空串即返回 true;`isNoneEmpty` 与 `!isAnyEmpty` 等价,所有参数均非空才为 true;`isBlank` 同时把空格视为空值;`isAnyBlank`、`isNoneBlank` 分别检测是否存在或全部不存在空格或空值。文末列出 `StringUtils` 其它常用方法(trim、equals、startsWith、split、replace、pad 等)并提供官方文档链接,帮助读者快速选用合适的字符串工具。

过多赠予,无所适从

本文以 Spring @Autowired 为例,解析“required a single bean, but 2 were found”错误的根源——在容器中存在同类型的多个 Bean,且缺乏 @Primary、@Priority 或名称匹配等优先级标识,导致 Spring 无法决定注入对象。通过源码剖析展示了 Bean 的实例化与属性填充过程以及 AutowiredAnnotationBeanPostProcessor 的工作原理。解决思路包括为其中一个实现加 @Primary、使用 @Qualifier 或通过属性名与 Bean 名称精确匹配等方式,以明确注入目标,进而消除冲突。

原型 Bean 被固定

Spring 中把 @Service 标记为原型(@Scope(ConfigurableBeanFactory.SCOPE_PROTOTYPE))的 Bean 注入到单例 @RestController 的字段时,Autowired 只在容器创建控制器时一次性实例化并固定该对象,导致原型作用失效并出现启动错误。源码分析显示 AutowiredAnnotationBeanPostProcessor 在 populateBean 阶段通过反射把找到的 Bean 直接赋值给字段,后续不再重新获取。解决办法有两种:①注入 ApplicationContext 并在方法中调用 applicationContext.getBean(ServiceImpl.class) 每次获取新实例;②在控制器中声明带 @Lookup 的抽象方法 getServiceImpl(),Spring 利用 CGLIB 生成子类并在调用时从 BeanFactory 动态获取原型 Bean。两种方式均能保证每次请求得到新的 ServiceImpl。文章还解释了 @Lookup 的实现原理以及 Spring 通过反射和方法覆盖实现原型注入的细节,提醒使用者注意单例‑原型混用的潜在陷阱。

定义的 Bean 缺少隐式依赖

文章指出,Spring 在创建标记为 @Service(或其他注解)的 Bean 时,如果该类显式声明了构造器,容器会依据构造器参数类型自动在 BeanFactory 中查找对应的 Bean 并注入。若参数(如 String)没有相应的 Bean,Spring 在 AbstractAutowireCapableBeanFactory#createBeanInstance → autowireConstructor → resolveDependency 过程中抛出 “Parameter … could not be found” 异常。解决办法是为构造器参数提供相应的 Bean(如通过 @Bean 定义 String serviceName()),或避免出现多个可选构造器导致歧义。文章提醒开发者不要把 Spring Bean 当作普通对象直接 new,需了解其隐式依赖规则,以免出现装配失败。

隐式扫描不到 Bean 的定义

Spring Boot 启动类使用 @SpringBootApplication 时,会自动开启 @ComponentScan,默认只扫描启动类所在包及其子包。将 Controller 移至其他包后,因未在扫描范围内,Spring 无法注册 HelloWorldController 为 Bean,导致接口失效。解决办法是显式指定扫描路径,例如在启动类上添加 @ComponentScan("com.zou.controller"),或使用 @ComponentScans 组合多个包。需要注意,显式配置后默认包不再自动扫描,须自行包含所有需要的包。

Java8新特性之Stream流

Stream 是 Java 8 处理集合的核心抽象,提供惰性求值、不可变数据源、可并行执行等特性。文章先介绍了 Stream 的分类(无状态/有状态、短路/非短路),随后列举了五种常用创建方式:Collection 的 stream()/parallelStream()、Arrays.stream、Stream.of/iterate/generate 以及 BufferedReader.lines、Pattern.splitAsStream。接着详细说明了中间操作——filter、limit、skip、distinct、map、flatMap、sorted、peek 等的使用场景和示例。随后阐述了终止操作,包括匹配/查找(allMatch、anyMatch、findFirst 等)、规约(reduce)以及收集(collect),并通过 Collectors 提供的 toList、toSet、toMap、joining、counting、summing、averaging、summarizing 等方法展示了如何将流结果转化为常用容器或统计信息。全文以代码示例为主,帮助读者快速掌握 Stream 的创建、转换、过滤、排序、终止及收集全过程。

全面拥抱Java17!

Java 17 作为自 Java 11 之后的下一个 LTS 版本,带来了多项语法升级,显著提升代码可读性和安全性。文章重点介绍了九大新特性:文本块让多行字符串编写更直观;switch 表达式支持返回值并可使用箭头语法简化分支;record 关键字提供简洁的不可变数据类;sealed class 通过 permits 限定子类继承范围;instanceof 模式匹配在判断时即完成类型转换并可配合条件表达式;Helpful NullPointerExceptions 在抛出空指针异常时指明具体的 null 来源;以及日期周期、紧凑数字格式化和 Stream.toList() 等实用改进。通过示例代码,作者展示了这些特性在实际开发中的使用方式,鼓励 Java 开发者全面迁移并利用 Java 17 提升生产力。

基于SpringBoot的在线招聘网站

本项目基于SpringBoot构建在线招聘平台,采用SpringBoot、MyBatisPlus、Layui、MySQL、Redis、Shiro、WebSocket、Thymeleaf等技术。实现游客可直接访问首页,点击“职位”“公司”自动跳转登录;登录使用kaptcha验证码,注册区分求职者和HR。求职者可按学历、经验、地点等条件筛选职位,查看详情并复制链接,在线聊天(含敏感词过滤),生成并复制简历链接,编辑个人信息。HR可修改资料,发布/管理岗位,管理员工,查看公司简介,聊天时直接打开职位或简历链接。管理员提供首页统计、聊天关系与记录查看,支持用户、简历、公司、岗位的增删改查及封禁违规用户等后台管理功能。

面试现场【Spring篇】

本文系统梳理了 Spring 面试常见知识点:列举了 Spring 使用的工厂、代理、单例、模板方法、观察者、适配器等设计模式;概述了 Core、Context、Web、MVC、DAO、ORM、AOP 等核心模块;阐释 IOC/DI 的本质、BeanFactory 与 ApplicationContext、FactoryBean 的区别以及 @Repository、@Service、@Component、@Controller 的分层意义;介绍 AOP 的概念、通知类型、动态/静态代理及 JDK 与 CGLIB 的实现差异,并比较 Spring AOP 与 AspectJ AOP;详细说明 Bean 的四阶段生命周期、三级缓存如何解决单例循环依赖以及为何需三级缓存;对比 @Autowired 与 @Resource 的注入策略;梳理 Spring 事务的五种隔离级别和七种传播行为;最后解析 Spring Boot 自动装配的 EnableAutoConfigurationImportSelector、spring.factories 与条件过滤机制。

遍历HashMap的几种方式及效率对比

文章通过两组各含100万条记录的HashMap,分别使用keySet、entrySet、values的Iterator和for‑each 方式遍历key、value或key‑value,并记录耗时。结果显示:① key 为连续整数时查找更快;② 大数据量下遍历key‑value最好使用entrySet(尤其配合for‑each);③ 若仅需value,直接遍历values最省时。由此推荐在实际开发中根据需求选择相应的遍历方式,以获得最佳性能。