Hessian 协议解释与实战(四):数组与集合

Hessian 协议解释与实战(四):数组与集合

D瓜哥
前段时间,翻译了 Hessian 2.0 的序列化协议,发布在了 Hessian 2.0 序列化协议(中文版)。但是,其中有很多言语不详之处。所以,接下来会用几篇文章来详细解释并实践一下 Hessian 序列化协议,以求做到知其然知其所以然。目录如下: Hessian 2.0 序列化协议(中文版) — Hessian 序列化协议的中文翻译版。根据后面的“协议解释与实战”系列文章,增加了协议内容错误提示。 Hessian 协议解释与实战(一):布尔、日期、浮点数与整数 — 介绍布尔型数据、日期类型、浮点类型数据和整数类型数据等四种类型的数据的处理。 Hessian 协议解释与实战(二):长整型、二进制数据与 Null — 介绍长整数类型数据、二进制数据和 null 等三种类型的数据的处理。 Hessian 协议解释与实战(三):字符串 — 专门介绍了关于字符串的处理。由于字符串需要铺垫的基础知识比较多,处理细节也有繁琐,所以单独成篇来介绍。 Hessian 源码分析(Java) — 开始第四篇分析之前,先来介绍一下 Hessian 的源码实现。方便后续展开说明。 Hessian 协议解释与实战(四):数组与集合 — 铺垫了一些关于实例对象的处理,重点介绍关于数组和集合的相关处理。 Hessian 协议解释与实战(五):对象与映射 — 重点介绍关于对象与映射的相关处理。 Avro、ProtoBuf、Thrift 的模式演进之路 — 翻译的 Martin Kleppmann 的文章,重点对比了 Avro、ProtoBuf、Thrift 的序列化处理思路。 在上一篇文章 Hessian 源码分析(Java) 对 Hessian 的 Java 实现做了一个概要的分析,对处理流程以及整体架构做了一个简单的分析。接下来,回到主题,继续来解释 Hessian 序列化协议。这篇文章,我们来重点分析一下数组与集合相关的操作。 基础工具方法 基础工具方法就不再赘述,请直接参考 Hessian 协议解释与实战(一):基础工具方法 中提到的几个方法。 对打印字符的工具做一下改造:
Hessian 源码分析(Java)

Hessian 源码分析(Java)

D瓜哥
前面通过几篇文章,解释并实践了一下 Hessian 的序列化协议。文章目录如下: Hessian 2.0 序列化协议(中文版) — Hessian 序列化协议的中文翻译版。根据后面的“协议解释与实战”系列文章,增加了协议内容错误提示。 Hessian 协议解释与实战(一):布尔、日期、浮点数与整数 — 介绍布尔型数据、日期类型、浮点类型数据和整数类型数据等四种类型的数据的处理。 Hessian 协议解释与实战(二):长整型、二进制数据与 Null — 介绍长整数类型数据、二进制数据和 null 等三种类型的数据的处理。 Hessian 协议解释与实战(三):字符串 — 专门介绍了关于字符串的处理。由于字符串需要铺垫的基础知识比较多,处理细节也有繁琐,所以单独成篇来介绍。 Hessian 源码分析(Java) — 开始第四篇分析之前,先来介绍一下 Hessian 的源码实现。方便后续展开说明。 Hessian 协议解释与实战(四):数组与集合 — 铺垫了一些关于实例对象的处理,重点介绍关于数组和集合的相关处理。 Hessian 协议解释与实战(五):对象与映射 — 重点介绍关于对象与映射的相关处理。 Hessian、Msgpack 和 JSON 实例对比 — 用实例对比 JSON、Hessian 和 MessagePack 的区别。 Avro、ProtoBuf、Thrift 的模式演进之路 — 翻译的 Martin Kleppmann 的文章,重点对比了 Avro、ProtoBuf、Thrift 的序列化处理思路。 该系列第四篇文章准备详细介绍一下 Hessian 对对象、链表以及 Map 等处理。但是,越调试代码,越发觉得应该先对 Hessian 的实现做一个源码分析。于是,就有了本文。 这里有几点需要声明一下: 在上面“解释与实战”系列文章中提到的代码就不再重复说明。 通过“解释与实战”系列文章,大家应该可以领略到,处理序列化有大量的细节。但是,本文并不打算涉及。本文重点是介绍 Hessian 的 Java 实现的架构蓝图。相当于给指明一条路,沿着这条路,大家就可以探索 Hessian 的各种细节。
Hessian 协议解释与实战(三):字符串

Hessian 协议解释与实战(三):字符串

D瓜哥
前段时间,翻译了 Hessian 2.0 的序列化协议,发布在了 Hessian 2.0 序列化协议(中文版)。但是,其中有很多言语不详之处。所以,接下来会用几篇文章来详细解释并实践一下 Hessian 序列化协议,以求做到知其然知其所以然。目录如下: Hessian 2.0 序列化协议(中文版) — Hessian 序列化协议的中文翻译版。根据后面的“协议解释与实战”系列文章,增加了协议内容错误提示。 Hessian 协议解释与实战(一):布尔、日期、浮点数与整数 — 介绍布尔型数据、日期类型、浮点类型数据和整数类型数据等四种类型的数据的处理。 Hessian 协议解释与实战(二):长整型、二进制数据与 Null — 介绍长整数类型数据、二进制数据和 null 等三种类型的数据的处理。 Hessian 协议解释与实战(三):字符串 — 专门介绍了关于字符串的处理。由于字符串需要铺垫的基础知识比较多,处理细节也有繁琐,所以单独成篇来介绍。 Hessian 源码分析(Java) — 开始第四篇分析之前,先来介绍一下 Hessian 的源码实现。方便后续展开说明。 Hessian 协议解释与实战(四):数组与集合 — 铺垫了一些关于实例对象的处理,重点介绍关于数组和集合的相关处理。 Hessian 协议解释与实战(五):对象与映射 — 重点介绍关于对象与映射的相关处理。 Hessian、Msgpack 和 JSON 实例对比 — 用实例对比 JSON、Hessian 和 MessagePack 的区别。 Avro、ProtoBuf、Thrift 的模式演进之路 — 翻译的 Martin Kleppmann 的文章,重点对比了 Avro、ProtoBuf、Thrift 的序列化处理思路。 在上一篇文章 Hessian 协议解释与实战(二):长整型、二进制数据与 Null 中研究了长整型、二进制数据与 null 等三种数据类型的处理方式。接下来,我们再来介绍字符串的处理情况。
Hessian 协议解释与实战(二):长整型、二进制数据与 Null

Hessian 协议解释与实战(二):长整型、二进制数据与 Null

D瓜哥
前段时间,翻译了 Hessian 2.0 的序列化协议,发布在了 Hessian 2.0 序列化协议(中文版)。但是,其中有很多言语不详之处。所以,接下来会用几篇文章来详细解释并实践一下 Hessian 序列化协议,以求做到知其然知其所以然。目录如下: Hessian 2.0 序列化协议(中文版) — Hessian 序列化协议的中文翻译版。根据后面的“协议解释与实战”系列文章,增加了协议内容错误提示。 Hessian 协议解释与实战(一):布尔、日期、浮点数与整数 — 介绍布尔型数据、日期类型、浮点类型数据和整数类型数据等四种类型的数据的处理。 Hessian 协议解释与实战(二):长整型、二进制数据与 Null — 介绍长整数类型数据、二进制数据和 null 等三种类型的数据的处理。 Hessian 协议解释与实战(三):字符串 — 专门介绍了关于字符串的处理。由于字符串需要铺垫的基础知识比较多,处理细节也有繁琐,所以单独成篇来介绍。 Hessian 源码分析(Java) — 开始第四篇分析之前,先来介绍一下 Hessian 的源码实现。方便后续展开说明。 Hessian 协议解释与实战(四):数组与集合 — 铺垫了一些关于实例对象的处理,重点介绍关于数组和集合的相关处理。 Hessian 协议解释与实战(五):对象与映射 — 重点介绍关于对象与映射的相关处理。 Hessian、Msgpack 和 JSON 实例对比 — 用实例对比 JSON、Hessian 和 MessagePack 的区别。 Avro、ProtoBuf、Thrift 的模式演进之路 — 翻译的 Martin Kleppmann 的文章,重点对比了 Avro、ProtoBuf、Thrift 的序列化处理思路。 在上一篇文章 Hessian 协议解释与实战(一) 中研究了布尔型数据、日期类型、浮点类型数据、整数类型数据等四种数据类型的处理方式。接下来,我们再来介绍长整数类型数据、二进制数据和 null 的处理情况。
Hessian 协议解释与实战(一):布尔、日期、浮点数与整数

Hessian 协议解释与实战(一):布尔、日期、浮点数与整数

D瓜哥
前段时间,翻译了 Hessian 2.0 的序列化协议,发布在了 Hessian 2.0 序列化协议(中文版)。但是,其中有很多言语不详之处。所以,接下来会用几篇文章来详细解释并实践一下 Hessian 序列化协议,以求做到知其然知其所以然。 目录如下: Hessian 2.0 序列化协议(中文版) — Hessian 序列化协议的中文翻译版。根据后面的“协议解释与实战”系列文章,增加了协议内容错误提示。 Hessian 协议解释与实战(一):布尔、日期、浮点数与整数 — 介绍布尔型数据、日期类型、浮点类型数据和整数类型数据等四种类型的数据的处理。 Hessian 协议解释与实战(二):长整型、二进制数据与 Null — 介绍长整数类型数据、二进制数据和 null 等三种类型的数据的处理。 Hessian 协议解释与实战(三):字符串 — 专门介绍了关于字符串的处理。由于字符串需要铺垫的基础知识比较多,处理细节也有繁琐,所以单独成篇来介绍。 Hessian 源码分析(Java) — 开始第四篇分析之前,先来介绍一下 Hessian 的源码实现。方便后续展开说明。 Hessian 协议解释与实战(四):数组与集合 — 铺垫了一些关于实例对象的处理,重点介绍关于数组和集合的相关处理。 Hessian 协议解释与实战(五):对象与映射 — 重点介绍关于对象与映射的相关处理。 Hessian、Msgpack 和 JSON 实例对比 — 用实例对比 JSON、Hessian 和 MessagePack 的区别。 Avro、ProtoBuf、Thrift 的模式演进之路 — 翻译的 Martin Kleppmann 的文章,重点对比了 Avro、ProtoBuf、Thrift 的序列化处理思路。 基础工具方法 Hessian 序列化之后的数据,都是字节数组,为了方便查看字节数组的二进制形式和十六进制形式,在正式开始之前,先介绍一下期间用到的辅助工具方法。闲言少叙,直接上代码: /** * 创建 Hessian2Output 对象,以便用于序列化 * * @author D瓜哥 · https://www.
Hessian 2.0 序列化协议(中文版)

Hessian 2.0 序列化协议(中文版)

D瓜哥
公司在微服务系统中,序列化协议大多数使用 MessagePack。但是,由于 MessagePack 设计限制,导致微服务接口在增减参数时,只能在最后操作。但是,由于个人操作,难免失误,结果造成因为增减字段导致的事故层出不穷。最近,一些条件成熟,准备推动部门将序列化协议切换到 Hessian。 原以为,切换到 Hessian 就可以万事大吉。但是,在和同事的沟通中发现,同事反馈,Hessian 本身也有一些限制。为了对 Hessian 有一个更深入的了解,干脆就把 Hessian 序列化协议读一遍。看协议,文字不多,干脆就把协议完整翻译一遍。闲言少叙,正文开始。 Hessian 2.0 序列化协议 协议解释 针对该协议有很多言语不详,甚至模糊不清之处,专门做了一些解释和实践,叙述系列文章,用于辅助消化理解。目录如下: Hessian 2.0 序列化协议(中文版) — Hessian 序列化协议的中文翻译版。根据后面的“协议解释与实战”系列文章,增加了协议内容错误提示。 Hessian 协议解释与实战(一):布尔、日期、浮点数与整数 — 介绍布尔型数据、日期类型、浮点类型数据和整数类型数据等四种类型的数据的处理。 Hessian 协议解释与实战(二):长整型、二进制数据与 Null — 介绍长整数类型数据、二进制数据和 null 等三种类型的数据的处理。 Hessian 协议解释与实战(三):字符串 — 专门介绍了关于字符串的处理。由于字符串需要铺垫的基础知识比较多,处理细节也有繁琐,所以单独成篇来介绍。 Hessian 源码分析(Java) — 开始第四篇分析之前,先来介绍一下 Hessian 的源码实现。方便后续展开说明。 Hessian 协议解释与实战(四):数组与集合 — 铺垫了一些关于实例对象的处理,重点介绍关于数组和集合的相关处理。 Hessian 协议解释与实战(五):对象与映射 — 重点介绍关于对象与映射的相关处理。 Hessian、Msgpack 和 JSON 实例对比 — 用实例对比 JSON、Hessian 和 MessagePack 的区别。 Avro、ProtoBuf、Thrift 的模式演进之路 — 翻译的 Martin Kleppmann 的文章,重点对比了 Avro、ProtoBuf、Thrift 的序列化处理思路。
在 Spring Boot 中 Jackson 日期格式化技巧

在 Spring Boot 中 Jackson 日期格式化技巧

D瓜哥
使用 Spring Boot 时,需要使用 Jackson 处理一些 Java Time API 类型的 JSON 序列化问题,在处理一些类的字段时,可以通过直接在属性上加注解的方式来指定其格式化样式。但是,昨天同事遇到一个格式化 Map 数据的问题,这样就不能通过加注解来解决格式化样式的问题了。 在网上各种搜索,各种尝试后,终于解决了这个问题,记录一下,以备不时之需。 闲言少叙,直接上代码: package com.diguage.demo.config; import com.fasterxml.jackson.databind.ObjectMapper; import com.fasterxml.jackson.databind.util.StdDateFormat; import com.fasterxml.jackson.datatype.jsr310.JavaTimeModule; import com.fasterxml.jackson.datatype.jsr310.deser.LocalDateDeserializer; import com.fasterxml.jackson.datatype.jsr310.deser.LocalDateTimeDeserializer; import com.fasterxml.jackson.datatype.jsr310.ser.LocalDateSerializer; import com.fasterxml.jackson.datatype.jsr310.ser.LocalDateTimeSerializer; import org.springframework.context.annotation.Bean; import org.springframework.context.annotation.Configuration; import org.springframework.context.annotation.Primary; import java.text.DateFormat; import java.text.SimpleDateFormat; import java.time.LocalDate; import java.time.LocalDateTime; import static com.fasterxml.jackson.databind.SerializationFeature.*; import static java.time.format.DateTimeFormatter.ofPattern; /** * 配置类 * * @author D瓜哥 · https://www.diguage.com */ @Configuration public class Config { /** * 创建 ObjectMapper 对象,配置日期格式化 * * @author D瓜哥 · https://www.
使用 Maven Enforcer 插件检查依赖

使用 Maven Enforcer 插件检查依赖

D瓜哥
最近公司项目要对一些内部依赖做集中升级。为此,D瓜哥发布了一个 BOM(BOM stands for Bill Of Materials),用于规范项目依赖及版本。 但是升级后,效果不理想,检查发现还是有不少依赖的版本依然不符合要求。经同事提醒,可以使用 Apache Maven Enforcer 来做规范检查,测试一下效果确实不错。 将 Apache Maven Enforcer 和 Extra Enforcer Rules 的文档大致巴拉了一遍之后,根据项目的实际情况,挑选出来可用规则如下: 比较有用的几个规则 bannedDependencies – 排除不需要的依赖,引入需要的依赖。 banDuplicatePomDependencyVersions – 防止依赖重复声明。 dependencyConvergence – 确保所有依赖收敛到相同的版本。也可以考虑加入。 reactorModuleConvergence – 多模块开发时,确保父子模块的版本是一致的。 requireJavaVersion – 检查 JDK 的版本 requireMavenVersion – 检查 Maven 的版本 requireReleaseVersion – 这个可以通过激活生产环境的 profile 来启用该规则,保证发布的不是快照版。 requireUpperBoundDeps – 确保直接引用的依赖不比间接解析出来的依赖版本低。感觉这个也挺有用,但是使用方式还没搞清楚。实例有些模糊。 banDuplicateClasses – 检查重复类定义。可以避免一些特殊情况。 requirePropertyDiverges – 确保项目定义的属性与依赖中包含的属性不重复。 enforceBytecodeVersion – 确保使用的字节码版本不高于指定版本。 banCircularDependencies – 确保没有循环依赖。 requireEncoding – 指定项目字符集。 实践总结 D瓜哥把上面的规则几乎全部试用了一遍,把发现的一些需要特别注意的地方标注记录一下吧:
《投资中最简单的事》之读书笔记(四):投资心理学

《投资中最简单的事》之读书笔记(四):投资心理学

D瓜哥
最近一位同事离职,在践行宴会上,大家聊到投资理财,D瓜哥推荐了 《投资中最简单的事》。去年已经把这本书读完了,下班后把这本书的摘要笔记整理一下,按照章节,分四篇来分享: 《投资中最简单的事》之读书笔记(一):投资理念 《投资中最简单的事》之读书笔记(二):投资方法 《投资中最简单的事》之读书笔记(三):投资风险 《投资中最简单的事》之读书笔记(四):投资心理学 第四部分 投资心理学 11 人性的弱点:投资者常见的心理误区 一个股票便宜与否,看估值比看近期涨跌更可靠:基本面大幅超预期时会越涨越便宜,反之会越跌越贵。 美国消费股多,适合价值投资;加拿大资源股多,适合趋势投资。互联网赢家通吃,买龙头;休闲服装百花齐放,买成长。差异化产品,买品牌;同质化产品,买成本低的。 俾斯麦说,每个笨蛋都会从自己的教训中吸取经验,聪明人则会从别人的经验中获益。 同样是错过航班,错过 3分钟的比错过 30分钟的更沮丧;同样是彩票没中,号码与头奖号码只差一点的是最痛苦的。 与成功擦肩而过比从未接近成功更令人难以接受,更令人想再试一次,所以,许多赌博形式正是包含大量“差点就赢”的设计,才吸引了这么多赌徒不惜倾家荡产屡败屡战。 12 后视镜 应该跑向球将要去的地方,而不是球现在所在的地方。 13 傻瓜定价说 对市场敬畏但不屈服,逆市场而动但懂得自我保护。 14 这次不同了 人们从历史中学到的唯一教训就是人们从来不吸取任何教训。 每一次危机或泡沫都感觉像是史无前例,其实不过是历史长河中的一朵浪花。 当人们在为“黄金十年”找论据时,市场离见顶就不远了;当人们在为长期的悲观寻找理由时,市场已经在底部区域了。投资者的悲哀,永远是轻易地放弃和错误地坚持。 15 树动风动心动 短期来说,股价波动是人心与人心博弈的结果,是心在动,难以预测。中期来说,股价更多是由政策面决定:吹的是政策宽松的暖风,股价就上涨;刮的是政策紧缩的寒风,股价就下跌。所以说,中期是风在动。 长期来说,股价是由基本面决定的。那些根基不稳的病树,难以避免在风中被连根拔起的命运;而那些有稳固根基的好树,不管人心冷暖,风向东西,终将成长为参天大树。所以说,长期是树在动。 “心在动”常对“风在动”推波助澜,把五级风放大为十级,此时人们已不关心“树动”与否,反正玩的是击鼓传花的游戏。 附录 投资访谈:顺应规律投资,才能事半功倍 过去 10年,人家问我看好什么行业,我在任何时候都是讲三大类行业:金融地产、品牌消费、先进制造。 有“霸王条款”的行业都不会太差。 便宜是硬道理,股票的回报并不取决于它未来的增长快还是慢,而是取决于未来增长比当前股价反映的增长预期更快还是更慢。 我们找白酒的顺序是先找高端,再找次高端,再到平价酒,因为中国经济的复苏通常是先重点扶持基建,商务应酬增加,对高端酒的需求会增加,之后经济恢复,老百姓有钱了,中端酒开始起来,然后再到低端酒。 市场是一个拍卖系统,最后的顶点总是最疯狂的人在定价,就像在拍卖会上面,最后的买主肯定是那个最狂热的、愿意出最高价的人。 一个投资人说过,当一家公司的创始人和管理者,主要是做好两点:一个是算命,即想清楚一些大的战略性的问题;第二是相面,就是选人。 后记 大佬为什么对科技股长期持谨慎的态度?为什么热衷科技股的基金经理鲜有长时间业绩突出者? 第一,科技进步内在的突变性决定了科技股投资人业绩内在的不可延续性。 第二,科学技术是不断变化的。 第三,虽然新技术的前景广阔,初期的行业格局却非常散乱,绝大多数投资人很难在事前判断出谁是最终赢家。 临渊羡鱼不如退而结网,投资必须把握你能把握的东西。 知道自己的能力边界,发挥自己的优势,买便宜的好公司,注意安全边际,注重定价权,人弃我取,在胜负已分的行业里找赢家,这些貌似投资中最简单的事,其实也是投资中最本质的东西。
《投资中最简单的事》之读书笔记(三):投资风险

《投资中最简单的事》之读书笔记(三):投资风险

D瓜哥
最近一位同事离职,在践行宴会上,大家聊到投资理财,D瓜哥推荐了 《投资中最简单的事》。去年已经把这本书读完了,下班后把这本书的摘要笔记整理一下,按照章节,分四篇来分享: 《投资中最简单的事》之读书笔记(一):投资理念 《投资中最简单的事》之读书笔记(二):投资方法 《投资中最简单的事》之读书笔记(三):投资风险 《投资中最简单的事》之读书笔记(四):投资心理学 第三部分 投资风险 07 价值陷阱与成长陷阱 价值陷阱 第一类是被技术进步淘汰的。 第二类是赢家通吃行业里的小公司。 集中度越来越高说明行业里的龙头企业比其他企业增长更快,不然就是越来越分散。 第三类是分散的、重资产的夕阳行业。 第四类是景气顶点的周期股。 对周期股价值的评估可以借助两个概念,一个是常态化的盈利( Normalized Earnings),计算剔除了经济周期波动后的企业盈利;另一个是盈利能力( Earnings Power),而不是某一时间的盈利数额,评估企业内在的可持续的盈利水平。 怎么操作? 第五类是有会计欺诈的公司。 最后一类是人不行、捧着“金饭碗”讨饭的公司。“ 金玉之堂,莫之能守 成长陷阱 成长陷阱比价值陷阱更常见。 估值过高 技术路径踏空 无利润增长 成长性破产 盲目多元化 树大招风 追随者挑战巨头的时候要小心,不要太早显露目的,以免遭到巨头的封杀和围剿。 新产品风险 寄生式增长 强弩之末 会计造假 各类价值陷阱的共性是利润的不可持续性,各类成长陷阱的共性是成长的不可持续性。 成长本身并不是陷阱,但人性的弱点中对未来成长习惯性地过高预期和过高估值却是不折不扣的陷阱。 管子说:“不为不可成,不求不可得,不处不可久,不行不可复。” “黄金坑”还是“融化中的冰棒” 这有点像一根正在融化的冰棒,你拿在手中它就不断地融化。 价值陷阱大部分的问题主要出现在内在逻辑被破坏,这样整个公司的护城河、核心竞争力逐步丧失,整个公司要么被时代淘汰,要么被对手打败,这种大多数是价值陷阱。 我们需要理解什么是永久性的下跌,什么是暂时性的调整。 如果找到了每一个公司便宜的原因,就能判断相应的股票是价值陷阱还是“黄金坑”。 趋势投资是可以不断止损的,每一次错误最大的损失是有限的。所以,从这个意义上看,价值投资的风险比趋势投资更大。 08 真假风险与安全边际 股市如围城,城内的人在往外逃,城外的人在往里冲。 在互联网时代,品牌的优势比渠道的优势更重要。 股票暴涨后,真实的风险上升,感受到的风险却在下降,在 6 000点股市最危险的时候大家感受到的都是歌舞升平;股票暴跌后,真实的风险下降,感受到的风险上升,在 2 000点股市相对低谷时人们感受到的却都是凄风苦雨。 黑色星期一之后暴露的风险很大,但是隐藏的风险不大;感受到的风险很大,但是真实的风险不大。能区分并利用这两种风险的不同,是成功投资的必要条件。 对于逆向投资者来说,最痛的时候,往往是最不该放手的时候。正如索罗斯所说,如果你承受不了失败的痛苦,就不要入市,因为没有人能够百战百胜。 安全边际 东方不亮西方亮,给点阳光就灿烂 估值低到足以反映大多数可能的坏情况 有“冗余设计”,有“备用系统”来限制下跌空间 价值易估,不具反身性,可越跌越买 索罗斯所说的反身性是指股价下跌本身对公司基本面有负面作用,易形成自我强化的恶性循环。 贝尔斯登和可口可乐对比!多思考!!! 鼻莫如大,目莫如小 止损 对于趋势投资者而言,止损不止赢是短线交易的第一法则,自不必多说。 忘掉你的成本,是成功投资的第一步。