摸鱼精选第 12 期

1. 多范式融合的现代 C++软件设计

本文介绍了 C++从过程式编程、面向对象编程、泛型编程、函数式编程这个趋势每个范式的优缺点。

函数式也不是银弹,也有局限性,尤其是建模受限。现代化 C++编程肯定是多范式融合的,从顶层设计上一定是面向对象设计的,局部模块过程式、泛型、函数式都可以,要根据具体情况来设计。

2. 一文聊透 Netty IO 事件的编排利器 pipeline

本文涉及到的内容比较多,通过 netty 异步事件在 pipeline 中的编排和传播这条主线,我们相当于将之前的文章内容重新又回顾总结了一遍。

本文中我们详细介绍了 pipeline 的组成结构,它主要是由 ChannelHandlerContext 类型节点组成的双向链表。ChannelHandlerContext 包含了 ChannelHandler 执行上下文的信息,从而可以使 ChannelHandler 只关注于 IO 事件的处理,遵循了单一原则和开闭原则。

此外 pipeline 结构中还包含了一个任务链表,用来存放执行 ChannelHandler 中的 handlerAdded 回调和 handlerRemoved 回调。pipeline 还持有了所属 channel 的引用。

我们还详细介绍了 Netty 中异步事件的分类:Inbound 类事件,Outbound 类事件,ExceptionCaught 事件。并详细介绍了每种分类下的所有事件的触发时机和在 pipeline 中的传播路径。

最后介绍了 pipeline 的结构以及创建和初始化过程,以及对 pipeline 相关操作的源码实现。

中间我们又穿插介绍了 ChannelHanderContext 的结构,介绍了 ChannelHandlerContext 具体封装了哪些关于 ChannelHandler 执行的上下文信息。

3. Swift 为自定义属性包装类型添加类 @Published 的能力

本文将对 @Published 与符合 ObservableObject 协议的类实例之间的沟通机制做以介绍,并通过三个示例:@MyPublished( @Published 的仿制版本 )、@PublishedObject(包装值为引用类型的 @Published 版本)、@CloudStorage(类似 @AppStorage ,但适用于 NSUbiquitousKeyValueStore ),来展示如何为其他的自定义属性包装类型添加可访问包裹其的类实例的属性或方法的能力。

4. Android 子线程 UI 操作真的不可以?

对于 Android 子线程不能操作 UI 的更深入理解:控制 View 绘制的线程和通知 View 更新的线程必须是同一线程,也即 UI 线程一致。

对于弹窗等与 App 其他业务相对独立的场景,可以考虑多 UI 线程优化。

后续工作中,清晰辨析 UI 线程、主线程、子线程的概念,尽量不要混用。

当然,多 UI 线程也有一些不适用的场景,如以下逻辑:

  • Webview 的所有方法调用必须在主线程,因为其代码中强制做了主线程校验,如 PopupWindow 中内置 Webview,则不适用多 UI 线程。

  • Activity 的使用必须在主线程,因为其创建等操作中使用的 Handler 也被强制指定为 mainThreadHandler。

5. Every SwiftUI Environment Value explained

SwiftUI 里面的环境变量总结。

6. 浅谈 Atomic CSS 的发展背景与 Tailwind CSS

Atomic CSS 诞生于雅虎的大型项目下,最重要的点是去掉了 Context 这个东西,无需在 CSS 里面写条件语句一样的代码:

media {
  margin: 10px;
}
.media,
.media .img {
  float: left;
  margin-right: 10px;
}
.media .img img {
  display: block;
}

.media .imgExt {
  float: right;
  margin-left: 10px;
}

#rightRail .bd {
  font-size: smaller;
}

Atomic CSS 的 class 是线性增长的,自由组合,用在现代化的 component 化的前端项目下是非常适合的,不论是 CSS in JS 还是 CSS Modules。

7. How fast are Linux pipes anyway?

本文作者试着优化 Linux 的管道速度,从 3.5 GB/s 提升 20 倍到 65 GB/s。

8. 微软教你学 Go 语言

会比 Google 教的更好吗?😄

9. Modern programming languages require generics

在作者看来,任何以高性能为目标的现代编程语言都应该有某种形式的泛型。作者本身是做数据库的,所以举了排序为例子。有泛型功能的编程语言会有性能上的提升,比如 C++、Java、Go。但 Java 是个特例,它不是在编译期决定的,而是在运行时判断不同类型,调用对应的 sort 方法。

作者在文中提到一篇文章"Faster sorting with Go generics",文中比较了用 Go 实现冒泡排序在使用泛型和不使用泛型时的性能,结果发现泛型版本会有 20%的性能提升。

Go 官方的sort 方法也已经改用泛型版本了,贡献者还是字节跳动的员工,采用了一种不稳定的 Pattern-defeating 快排算法,比原来的内置版本快 2-60 倍的速度。

10. 从零开始写数据库:500 行代码实现 LSM 数据库

LSM-Tree 是很多 NoSQL 数据库引擎的底层实现,例如 LevelDB,Hbase 等。本文基于《数据密集型应用系统设计》中对 LSM-Tree 数据库的设计思路,结合代码实现完整地阐述了一个迷你数据库,核心代码 500 行左右,通过理论结合实践来更好地理解数据库的原理。

可以结合作者另一篇文章《从零开始写 KV 数据库:基于哈希索引》看看。

11. 现代 C++测试工具链(是时候抛弃 gtest/google bench 了)

本文介绍了 GTest 和 Google Bench 的替代品:

12. React 技术揭秘

本书的宗旨是打造一本严谨、易懂的 React 源码分析教程。

13. A lock-free, concurrent, generic queue in 32 bits

一个 32 位的无锁、并发、通用的队列。

14. Go 语言使用的 TCMolloc 内存分配器

15. Http2 讲解

这是一篇详细讲解 HTTP/2(RFC 7540)的文档,主要内容包括该协议的背景、思想、协议本身的内容、对一些现有实现的探讨与对协议未来的展望。

16. Host a Ghost 5.0 Blog for Free on Fly.io — In 1 Minute

只要一分钟即可在 Fly.io 上部署 Ghost 5.0 博客。