Ssmallcooldannyupdate readme
c8458a37创建于 2023年5月18日历史提交

OkHttp的低层IO库-io4cj

OkHttp的低层IO库——io4cj,io4cj是对仓颉io库的补充,使访问、存储和处理数据变得更加容易。

Segment与Segment Pool

io4cj数据移动这一块,主要由3个关键类

  • Buffer 里面保存了一个segment双向循环链表,从head segment读取,从tail segment写入
  • Segment 真正保存数据的类,pos和limit保存了可以读写的位置,shared和owner表示是否可以修改此Segment里面的值
  • SegmentPool 保存了一个单向Segment链表,最大包含有8个Segment。recylce方法加入SegmentPool和take从SegmentPool里面读取,都是从next节点(链表的头节点)开始的

ByteString与Buffer

io4cj是围绕这两种类型构建的,它们将大量功能集成到了简单的API中:

ByteString 是一个不可变的字节序列,String的基础是字符,而ByteString就像是String的兄弟一样,它可以轻松将二进制数据视为某些值。这个类非常聪明:它知道如何对自己进行十六进制,base64和UTF-8编码和解码。

Buffer 是可变的字节序列。与ArrayList一样,无需预先设置缓冲区大小。以队列的方式读取和写入缓冲区:将数据写入末尾,然后从队列头部读取。没有必要去管理读取位置,范围或容量。

在内部,ByteString和Buffer做一些巧妙的事情来节省CPU和内存。 如果将UTF-8字符串编码为ByteString,它会缓存对该字符串的引用,以便以后进行解码时无需做任何工作。

缓冲区被实现为段的链表。当您将数据从一个缓冲区移到另一个缓冲区时,它会重新分配段的所有权,而不是跨缓冲区复制数据。这种方法对多线程程序特别有用:与网络请求相关的线程可以与工作线程交换数据,而无需任何复制或多余的操作。

open public class ByteString {
	open fun asByteBuffer(): ArrayList<Byte>
	func base64(): String
	func base64Url(): String
	...
}
interface BufferedSource <: Source {
	func close(): Unit
	func exhausted(): Bool
	func indexOf(b: Byte): Int64
	func read(p0: ByteBuffer): Int64
	...
}
interface BufferedSink <: Sink {
	func close(): Unit
	func emit(): BufferedSink
	func flush()
	func write(p0: ByteBuffer): Int64
	...
}

Source与Sink

对流进行分层来处理加密和压缩等转换,Source和Sink,分别类似于仓颉的ReadStream和WriteStream

  • 超时(Timeout):流提供了对底层I/O超时机制的访问。与java.io的socket字节流不同,read()和write()方法都给予超时机制。
  • 实现简单: Source只声明了三个方法:read()、close()和timeout()。没有像available()或单字节读取这样会导致性能下降问题。
  • 使用方便:虽然source和sink中只有三个方法需要实现,但是调用方可以实现Bufferedsource和Bufferedsink接口,这两个接口提供了丰富API能够满足你所需要的一切。
  • 字节流和字符流的处理没有直观的区别:因为它们都是数据。你可以以字节、UTF-8字符串、big-endian的32位整数、little-endian的短整数等任何你想要的形式进行读写;再也不需要InputStreamReader!
  • 测试简单: Buffer类同时实现了BufferedSource和BufferedSink,因此测试代码简单明了。

Sources 和 Sinks分别与InputStream和OutputStream交互操作。你可以将任何Source看做InputStream ,也可以将任何InputStream当做Source。对于Sink和Outputstream也是如此。

interface Sink <: ReadStream {
	func close(): Unit
	func flush(): Unit
	func timeout(): Duration
	func write(source: Buffer, byteCount: Int64): Unit
	...
}
interface Source <: ReadStream {
	func close(): Unit
	func read(sink: Buffer, byteCount: Int64): Int64
	func timeout(): Duration
	...
}

参考

参考项目: