SpringBoot中这样用ObjectMapper,才够优雅!

ObjectMapper 对象的基本使用(二) 阅读详情

👉 这是一个或许对你有用的社群

🐱 一对一交流/面试小册/简历优化/求职解惑,欢迎加入「芋道快速开发平台」知识星球。下面是星球提供的部分资料: 

64415881cef773bb99821d0bedc2cfa9.gif

👉这是一个或许对你有用的开源项目

国产 Star 破 10w+ 的开源项目,前端包括管理后台 + 微信小程序,后端支持单体和微服务架构。

功能涵盖 RBAC 权限、SaaS 多租户、数据权限、商城、支付、工作流、大屏报表、微信公众号、CRM 等等功能:

  • Boot 仓库:https://gitee.com/zhijiantianya/ruoyi-vue-pro

  • Cloud 仓库:https://gitee.com/zhijiantianya/yudao-cloud

  • 视频教程:https://doc.iocoder.cn

【国内首批】支持 JDK 21 + SpringBoot 3.2.2、JDK 8 + Spring Boot 2.7.18 双版本 

来源:JAVA日知录

220d52d8fd0d90e2f464bda8bbfba4fc.jpeg


每次new一个

在SpringBoot项目中要实现对象与Json字符串的互转,每次都需要像如下一样new 一个ObjectMapper对象:

public UserEntity string2Obj(String json) throws JsonProcessingException {
        ObjectMapper objectMapper = new ObjectMapper();
        return objectMapper.readValue(json, UserEntity.class);
        }

public String obj2String(UserEntity userEntity) throws JsonProcessingException {
        ObjectMapper objectMapper = new ObjectMapper();
        return objectMapper.writeValueAsString(car)
        }

这样的代码到处可见,有问题吗?

你要说他有问题吧,确实能正常执行;可你要说没问题吧,在追求性能的同学眼里,这属实算是十恶不赦的代码了。

首先,让我们用JMH对这段代码做一个基准测试,让大家对其性能有个大概的了解。

基准测试是指通过设计科学的测试方法、测试工具和测试系统,实现对一类测试对象的某项性能指标进行定量的和可对比的测试。而JMH是一个用来构建,运行,分析Java或其他运行在JVM之上的语言的 纳秒/微秒/毫秒/宏观 级别基准测试的工具。

@BenchmarkMode(Mode.Throughput)
@OutputTimeUnit(TimeUnit.SECONDS)
@State(Scope.Thread)
@Fork(1)
@Warmup(iterations = 5, time = 1)
@Measurement(iterations = 3, time = 1)
public class JsonJMHTest {

    String json = "{\"id\":122345667,\"email\":\"jianzh5@163.com\",\"price\":12.25}";
    UserEntity userEntity = new UserEntity(13345L,"jianzh5@163.com", BigDecimal.valueOf(12.25));
    /**
     * 测试String to Object
     */
    @Benchmark
    public UserEntity objectMapper2ObjTest() throws JsonProcessingException {
        ObjectMapper objectMapper = new ObjectMapper();
        return objectMapper.readValue(json, UserEntity.class);
    }

    /**
     * 测试Object to String
     */
    @Benchmark
    public String objectMapper2StringTest() throws JsonProcessingException {
        ObjectMapper objectMapper = new ObjectMapper();
        return objectMapper.writeValueAsString(userEntity);
    }

    public static void main(String[] args) throws RunnerException {
        Options opt = new OptionsBuilder()
                .include(JsonJMHTest.class.getSimpleName())
                .build();
        new Runner(opt).run();
    }
}

测试环境

> 基于 Spring Boot + MyBatis Plus + Vue & Element 实现的后台管理系统 + 用户小程序,支持 RBAC 动态权限、多租户、数据权限、工作流、三方登录、支付、短信、商城等功能
>
> * 项目地址:<https://github.com/YunaiV/ruoyi-vue-pro>
> * 视频教程:<https://doc.iocoder.cn/video/>

# JMH version: 1.36
        # VM version: JDK 17.0.3, OpenJDK 64-Bit Server VM, 17.0.3+7-LTS
        # Mac AppleM1/16GB

测试结果

94c56552c9b61116bfe58c3e757d75de.png

通过测试结果可以看出,每次new一个ObjectMapper,在实现字符串转对象时每秒可以完成23万多次,而实现对象转Json字符串每秒仅可完成2.7万次。

4de0bc400cc6c18873ddc27547c5e1ad.png

那该如何优化,提升性能呢?

基于 Spring Cloud Alibaba + Gateway + Nacos + RocketMQ + Vue & Element 实现的后台管理系统 + 用户小程序,支持 RBAC 动态权限、多租户、数据权限、工作流、三方登录、支付、短信、商城等功能

  • 项目地址:https://github.com/YunaiV/yudao-cloud

  • 视频教程:https://doc.iocoder.cn/video/

单例化

老鸟们都知道,在创建工具类时要将工具类设置成单例的,这样不仅可以保证线程安全,也可以保证在系统全局只能创建一个对象,避免频繁创建对象的成本。

所以,我们可以在项目中构建一个ObjectMapper的单例类。

@Getter
public enum ObjectMapperInstance {

    INSTANCE;

    private final ObjectMapper objectMapper = new ObjectMapper();

    ObjectMapperInstance() {

    }
}

再次使用JMH对其测试:

@Benchmark
public UserEntity singleten2ObjTest() throws JsonProcessingException {
        ObjectMapper objectMapper = ObjectMapperInstance.INSTANCE.getObjectMapper();
        return objectMapper.readValue(json, UserEntity.class);
        }

@Benchmark
public String singleten2StringTest() throws JsonProcessingException {
        ObjectMapper objectMapper = ObjectMapperInstance.INSTANCE.getObjectMapper();
        return objectMapper.writeValueAsString(userEntity);
        }

测试结果如下:

7b7bb03c82c45fcd07ca189139c48616.png

可以看到,使用单例模式,String转对象的方法每秒可以执行420多万次,比new ObjectMapper的方式快了18倍;而对象转String的方法每秒可以执行830万次,性能提升了300倍(看到结果的一瞬间我傻眼了,一度怀疑是写错代码了)!!!!

个性化配置

当然,在项目中使用ObjectMapper时,有时候我们还需要做一些个性化配置,比如将Long和BigDemical类型的属性都通过字符串格式进行转换,防止前端使用时丢失数值精度。

这些类型转换的格式映射都可以在单例类中配置,代码如下:

@Getter
public enum ObjectMapperInstance {

    INSTANCE;

    private final ObjectMapper objectMapper;

    ObjectMapperInstance() {
        objectMapper = new ObjectMapper();
        // 注册自定义模块
        initialize();
    }

    private void initialize() {
        CustomJsonModule customJsonModule = new CustomJsonModule();
        objectMapper.registerModule(customJsonModule);
    }
}

在initialize()方法中给ObjectMapper注册自定义序列化转换器。

355f577e5f0f65dfa068d2ed60a43020.png

第一行是使用注册自定义序列换转换器后的效果,给id和price字段都加上了引号。

再来一次JMH测试:

7026f3afec2e4bee693a2c0659a23501.png

可以看到,给ObjectMapper额外注册转换类型以后性能会受到一定的影响,但对业务影响不大。(啥业务能这么高的请求~)

小结

通过上面的测试,结论已经很清晰了。使用单例模式进行字符串转对象时性能可以提升18倍,而对象转String性能快了惊人的290万倍,所以在Spring中如何正确的使用ObjectMapper不用我再说了吧~


欢迎加入我的知识星球,全面提升技术能力。

👉 加入方式,“长按”或“扫描”下方二维码噢:

b961a40a181d9d011829b649026916f1.png

星球的内容包括:项目实战、面试招聘、源码解析、学习路线。

e205e85cd5718777bcae3c077e439269.png

467c175ba495c0352ceb1cb978c7707c.pngad91b40df1efba13bad33ca7f164c9c9.png9beebcd9ce493ef74bf2509b55a749f7.png45f76223a07d07884fbe80b79f77feb6.png

文章有帮助的话,在看,转发吧。
谢谢支持哟 (*^__^*)
SpringBoot中Jackson ObjectMapper配置、注解与实战避坑指南 JSON序列化与反序列化是现代Web开发中处理数据交换的基础技术,其核心原理是将内存中的对象结构转换为可传输或存储的字符串格式,反之亦然。这项技术对于构建高效、可维护的RESTful API和微服务架构具有关键价值,广泛应用于前后端分离、服务间通信和数据持久化等场景。在Java生态中,Jackson库因其强大的功能和稳定性成为SpringBoot项目的默认选择。本文聚焦于Jackson的核心组件ObjectMapper,深入解析其配置项、常用注解及性能优化策略,旨在帮助开发者解决日期格式处理、多态类型序列化 阅读详情

相关推荐

SpringBoot2实战:如何避免Jackson配置踩坑?手把手教你优雅定制ObjectMapper

本文深入解析SpringBoot2项目中Jackson的配置陷阱与最佳实践。针对常见的日期解析、Long类型精度丢失等问题,重点介绍了如何通过Jackson2ObjectMapperBuilderCustomizer进行安全、优雅的个性化定制,避免直接覆盖ObjectMapper导致的默认配置丢失,从而构建高可控的JSON处理引擎。

ii567的博客 749

SpringBoot教程(10) Jackson ObjectMapper使用和常用注解

Jackson详细教程一、前言二、ObjectMapper三、反序列化 一、前言 Jackson和Fastjson都是比较出名的JSON解析库,SpringMVC默认使用的是Jackson,而且在企业项目中也大多使用的是Jackson,感觉还是很有必要熟悉Jackson的基本使用的。 二、ObjectMapper Jackson最常用的的就是ObjectMapper, 它可以 三、反序列化 ...

Java Spring Elasticsearch 1万+

springboot2优雅个性化定制Jackson配置

Spring Boot2优雅个性化定制Jackson

q283614346的博客 4532

58、SpringBoot 配置及定制Jackson的ObjectMapper-->ObjectMapper 是 Jackson 来处理 Json 以及 xml 转换的一个核心 API

springboot 配置及定制Jackson的ObjectMapper,ObjectMapper 是 Jackson 来处理 Json 以及 xml 转换的一个核心 API

Java 领域技术分享 4308

SpringBoot开发——使用ObjectMapper处理JSON数据

SpringBoot开发——使用ObjectMapper处理JSON数据

bjzhang75的博客 998

Java json工具类,jackson工具类,ObjectMapper工具类

NULL 博文链接:https://fanshuyao.iteye.com/blog/2319705

SpringBoot 实战:在 RequestBody 中优雅的使用枚举参数(原理篇)_springboot requestbody 枚举

本文通过一个示例串起来注解起作用的逻辑,接口的逻辑与之类型,可以耐心debug一番。看完上述知识点如果你深感Java基础不够扎实,或者刷题刷的不够、知识不全面小编专门为你量身定制了一套针对知识面不够,也莫慌!还有一整套的,可以瞬间查漏补缺全都是一丢一丢的收集整理纯手打出来的。

2401_84435739的博客 1101

【学习笔记】计算机网络 第八章 无线局域网(WLAN)

计算机网络 第八章 无线局域网(WLAN)

Vera_shsf的博客 1244

SpringBoot jackson objectMapper 反序列化日期dateFormat扩展

yyyy-MM-dd HH:mm:ss 这种格式的日期在项目中非常的常用,但是SpringBoot使用个jackson却默认不支持这种日期的反序列化,那就只有我们自己来实现它了,非常的简单粗暴.. 我们只需要覆盖jackson的objectMapper类里边的dateFormat...

chuozhi8096的博客 4975

Anylabeling与SAM协同:从智能标注到YOLO数据集构建的完整实践

本文详细介绍了Anylabeling与SAM协同标注的完整实践,从智能标注到YOLO数据集构建的全流程。通过结合SAM的自动分割能力和Anylabeling的交互式标注,显著提升标注效率,特别适合小样本、复杂形状和多类别标注场景。文章还提供了环境搭建、标注优化技巧以及YOLO格式转换的实用指南。

weixin_26873711的博客 463

跨境TRS投资操作指南与系统解决方案

3 点击【申请 TRS 账户】,查看风险披露,录入账户参数、确定录入的参数信息,进行身份验证,输入验证码,TRS 账户开户申请已提交,后台对已提交的 TRS 开户申请进行审核,审核成功后,短信邮箱提醒,进行登录;2.点击【申请TRS账户】,查看风险披露,录入账户参数、确定录入的参数信息,进行身份验证,输入验证码,TRS账户开户申请已提交,后台对已提交的TRS开户申请进行审核,审核成功后,短信邮箱提醒,进行登录;4)更广泛的投资选择:相比A股通,TRS可以交易更多的A股标的,提供了更广泛的投资选择。

2401_85487119的博客 2853

SpringBoot 实战:在 RequestBody 中优雅的使用枚举参数(原理篇)

该图片由Johnnys_pic在Pixabay上发布 你好,我是看山。 在优雅的使用枚举参数(原理篇)中我们聊过,Spring对于不同的参数形式,会采用不同的处理类处理参数,这种形式,有些类似于策略模式。将针对不同参数形式的处理逻辑,拆分到不同处理类中,减少耦合和各种if-else逻辑。本文就来扒一扒,RequestBody参数中使用枚举参数的原理。 找入口 对 Spring 有一定基础的同学一定知道,请求入口是DispatcherServlet,所有的请求最终都会落到doDispatch方法中的h..

沉潜飞动 5372

【电路设计实战】BUCK降压电路:从原理到PCB布局的降噪与效率优化

本文深入剖析了BUCK降压电路的工作原理,并针对其固有的开关噪声问题,提供了从核心元件选型到PCB布局的全面优化方案。文章重点探讨了电感、电容等关键元件的选型要点,强调了低ESR电容和肖特基二极管的重要性,并详细阐述了如何通过最小化功率回路、保护敏感信号线等PCB布局实战技巧,有效抑制噪声、提升效率与稳定性。

weixin_29304021的博客 232

SpringBoot中如何优雅地个性化定制Jackson

下面,我们将了解如何自定义 Spring Boot 使用的默认ObjectMapper。@BeanSpringBoot 将自动注册com.fasterxml.jackson.databind.Module类型的任何 bean。在本文中,我们了解了在使用 SpringBoot 时配置 JSON 序列化选项的几种方法。我们看到了两种不同的方法:配置默认选项或覆盖默认配置。

tangjieqing的博客 1010

secureCRT 破解方法

3、输入注册信息打开keygen.exe,点击path,选择SecureCRT的安装目录(例如D:\VanDykeSoftware\Clients)的securecrt.exe打开,继续下一步打开LicenseHelper.exe,如下。1、注册SecureCRT9.1打开keygen.exe,出现以下问题(没有关掉安全防护,一双击打开,Windows会自动识别keygen.exe为bingdu并删除)打开桌面SecureCRT,此界面不输入内容,直接点击下一步。2、存储配置文件夹(可以默认安装)

逆水行舟 1万+

华为OD机试双机位C卷-几何平均值最大子数组(Py/Java/C/C++/Js/Go)

华为OD机试(机考)2026双机位C卷 【几何平均值最大子数组】,提供C语言、Java、C++、Python、Go、JavaScript源码实现,并提供完整思路讲解,以及在线OJ模拟做题。华为OD机试真题【几何平均值最大子数组】。

qq_45776114的博客 1368

SpringBoot+Jackson开发必看:如何用@JsonAlias优雅解决第三方API字段变更问题

本文深入探讨了在SpringBoot开发中,如何利用Jackson的@JsonAlias注解优雅应对第三方API字段变更的挑战。通过对比@JsonProperty,详细解析了@JsonAlias在反序列化中实现一对多字段映射的优势,并提供了从基础实体设计到高级策略封装的完整实战方案,帮助开发者构建高兼容、易维护的接口适配层,有效隔离外部变化。

milk8的博客 448

机加工机器人系列编程:Fanuc M-710iC_(2).FanucM-710iC机器人的硬件配置

Fanuc M-710iC 机器人是一种广泛应用在汽车零部件制造行业中的工业机器人。它的本体结构设计紧凑、稳定,适用于多种加工任务。了解机器人的本体结构是进行编程和维护的基础。

zhubeibei168的博客 994

springboot2.0中@ResponseBody返回null值转空字符串的问题

最近正在做一个后台管理系统的项目,前端是基于Metronic的Bootstrap开发框架,管理后台大部分是将服务端查询的数据显示在表格中,由于某些字段可能为空,显示在表格中为null,不太优雅,所以想显示成空字符串或者“-”,服务端是spring boot2.0,过滤null值为空字符串一般是在序列化的时候设置值。 controller层使用@ResponseBody...

风雨诗轩的博客 3253

人形机器人新产品导入(NPI)工艺工程师的角色与技术解析

本文系统解析人形机器人NPI工程师的核心职责与能力要求。主要内容包括:1)NPI工程师需主导装配工艺设计、样品试做及问题闭环,涉及公差分析(如尺寸链计算)、工艺评审与FMEA应用;2)要求输出完整工艺文档体系,并跟踪试产至量产全过程;3)任职资格强调3年以上机器人/智能制造行业经验,掌握SPC、公差计算等质量工具,熟悉点胶/焊接等工艺及特殊材料特性;4)通过实际案例展示关节精度优化、新物料验证等典型工作场景;5)提供基于职责的面试问题及技术性解答方案。文章聚焦技术细节,为从业者提供实用参考框架。

郑伟强dev的专栏 382

OV9734 DATASHEET,完整规格书

OV9734完整规格书,包括电气参数,尺寸规格,寄存器配置表等

SpringBoot中使用Jackson将null值转化为""

SpringBoot中使用Jackson将null值转化为"" 前言:在实际项目中难免会遇到null值的出现,但是我们转json时并不希望出现NULL值,而是将NULL值转化为 “” 这种空的字符串。那么,我们应该如何处理呢?在SpringBoot中,新建一个配置类即可。 @Configuration public class JacksonConfig { @Bean @Pri...

橙子君的博客 7827

lwip-2.0.3

lwip是瑞典计算机科学院(SICS)的Adam Dunkels 开发的一个小型开源的TCP/IP协议栈。实现的重点是在保持TCP协议主要功能的基础上减少对RAM 的占用。

SpringBoot 优雅地对接口进行数据加解密

这日,刚撸完2两代码,正准备掏出手机摸鱼放松放松,只见老大朝我走过来,并露出一个”善意“的微笑,兴伟呀,xx项目有于安全问题,需要对接口整体进行加密处理,你这方面比较有经验,就给你安排上了哈,看这周内提测行不…,额,摸摸头上飘摇着而稀疏的长发,感觉我爱了。和产品、前端同学对外需求后,梳理了相关技术方案,经测试,响应数据和非加密版万全一致啦,还有GET部分的请求加密,以及后面加解密惨遭跨域问题,后面有空再和大家聊聊。SpringBoot 优雅地对接口进行数据加解密。

欢迎来到 ABin-阿斌的博客:写一生代码,创一世佳话,筑一览芳华。 616

VC中sqlite的使用

在VC中对sqlite的使用,实现数据库大批数据的快速插入,读取数据库中的数据在ListCtrl中显示

IDEA的使用指南

IDEA基于java的使用手册,可以最快速的上手,在使用中不断的丰富自己的使用技巧.

SpringBoot与XML交互全攻略:从手动拼接字符串到Jackson-dataformat-xml优雅实现

本文详细介绍了在SpringBoot项目中处理XML交互的完整方案,重点对比了手动拼接字符串的弊端与使用Jackson-dataformat-xml的优雅实现。通过依赖配置、核心注解详解及实战案例,指导开发者如何高效处理XML请求与响应,实现Java对象与XML间的声明式映射,提升代码可维护性和开发效率。

q6r7s8t9的博客 675
上一篇: 彻底告别 Controller、Service、Dao,让人上瘾的开发神器...
下一篇: 别再用“! = null”做判空了!Optional更好用!
公众号-芋道源码
博客等级 码龄10年 1636粉丝 377原创
评论 1
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值