本书github链接:inside-rust-std-library
前面章节参见:
深入RUST标准库内核(序言) - 简书 (jianshu.com)
深入RUST标准库内核(一 概述) - 简书 (jianshu.com)
深入RUST标准库内核(二 内存)—Layout/原生指针 - 简书 (jianshu.com)
深入RUST标准库内核(二 内存)—NonNull<T>/申请及释放 - 简书 (jianshu.com)
深入RUST标准库内核(二 内存)—mem模块/MaybeUninit<T> - 简书 (jianshu.com)
深入RUST标准库内核 (三 基础Trait) 编译器内置Trait - 简书 (jianshu.com)
深入RUST标准库内核(三 基础Trait)— Ops Trait - 简书 (jianshu.com)
深入RUST标准库内核(三 基本Trait)—Range - 简书 (jianshu.com)
深入RUST标准库内核(三 基础Trait)—Index Trait - 简书 (jianshu.com)
深入RUST标准库内核(四 Iterator 实现)— Range实现 - 简书 (jianshu.com)
深入RUST标准库内核(四 Iterator)— Slice实现 - 简书 (jianshu.com)
深入RUST标准库内核(四 Iterator 实现)— str及array实现 - 简书 (jianshu.com)
Iterator的适配器代码分析
Map 适配器代码分析
Map相关代码如下:
pub trait Iterator {
//其他内容
...
...
//创建map Iterator
fn map<B, F>(self, f: F) -> Map<Self, F>
where
Self: Sized,
F: FnMut(Self::Item) -> B,
{
Map::new(self, f)
}
...
}
//此结构是一个adapter的结构
pub struct Map<I, F> {
// Map的底层Iterator
pub(crate) iter: I,
// Map操作闭包函数
f: F,
}
impl<I, F> Map<I, F> {
//由Iterator::map 函数和这个函数可以理解Iterator的lazy特性,
//Iterator的创建实际上仅仅建立了数据结构,直到next才有操作。
pub(in crate::iter) fn new(iter: I, f: F) -> Map<I, F> {
Map { iter, f }
}
}
//针对Map实现Iterator
impl<B, I: Iterator, F> Iterator for Map<I, F>
where
F: FnMut(I::Item) -> B,
{
type Item = B;
fn next(&mut self) -> Option<B> {
//利用底层Iterator的next,Option::map实现next
self.iter.next().map(&mut self.f)
}
fn size_hint(&self) -> (usize, Option<usize>) {
self.iter.size_hint()
}
//其他函数,其实现技巧与next类似
...
...
}
Chain 适配器代码分析
相关代码如下:
pub trait Iterator {
...
...
//创建Chain Iterator
fn chain<U>(self, other: U) -> Chain<Self, U::IntoIter>
where
Self: Sized,
U: IntoIterator<Item = Self::Item>,
{
Chain::new(self, other.into_iter())
}
...
...
}
pub struct Chain<A, B> {
a: Option<A>,
b: Option<B>,
}
impl<A, B> Chain<A, B> {
pub(in super::super) fn new(a: A, b: B) -> Chain<A, B> {
Chain { a: Some(a), b: Some(b) }
}
}
macro_rules! fuse {
($self:ident . $iter:ident . $($call:tt)+) => {
//$iter可能已经被置为None
match $self.$iter {
//若$iter不为None,则调用iter的系列函数
Some(ref mut iter) => match iter.$($call)+ {
//函数返回None
None => {
//设置$iter为None,并返回None
$self.$iter = None;
None
}
//其他返回函数返回值
item => item,
},
//a为None时返回None
None => None,
}
};
}
//与fuse类似,略
macro_rules! maybe {
($self:ident . $iter:ident . $($call:tt)+) => {
match $self.$iter {
Some(ref mut iter) => iter.$($call)+,
None => None,
}
};
}
impl<A, B> Iterator for Chain<A, B>
where
A: Iterator,
B: Iterator<Item = A::Item>,
{
type Item = A::Item;
fn next(&mut self) -> Option<A::Item> {
//先执行self.a.next
match fuse!(self.a.next()) {
//若self.a.next返回None,则执行self.b.next
None => maybe!(self.b.next()),
//不为None,返回a的返回值
item => item,
}
}
...
...
}
其他
Iterator的adapter还有很多,如StedBy, Filter, Zip, Intersperse等等。具体请参考标准库手册。基本上所有的adapter都是遵循Adapter的设计模式来实现的。
小结
RUST的Iterater的adapter是突出的体现RUST的语法优越性的特性,借助Trait和强大的泛型机制,与c/c++/java/python/go相比较,RUST以很少的代码在标准库就实现了最丰富的adapter。而其他语言往往需要语言基础之上的框架去支持,会导致额外的学习努力。
函数式编程的基础框架之一便是基于Iterator和闭包实现丰富的adapter。这也凸显了RUST在语言级别对函数式编程的良好支持。