“特性”(或Perl中的“角色”)是一种将多个功能单元添加到类(或Rust中的struct)的方法,而没有多重继承的问题。特质是“跨领域关注点”,这意味着它们不属于类层次结构,可以在任何类上实现。
特性定义了一个接口,这意味着为了使任何东西实现该特性,它必须定义所有必需的方法。就像您可以要求方法参数属于某些类一样,您可以要求某些参数实现某些特征。
一个很好的例子是写输出。在许多语言中,您必须决定要写的是FileHandle对象还是Socket对象。这可能会令人沮丧,因为有时事情只会写入文件,而不会写入套接字,反之亦然,或者您可能希望捕获字符串中的输出以进行调试。
如果改为定义特征,则可以写入实现该特征的任何内容。这正是Rust所做的std::io::Write。
pub trait Write {
fn write(&mut self, buf: &[u8]) -> Result<usize>;
fn flush(&mut self) -> Result<()>;
fn write_all(&mut self, mut buf: &[u8]) -> Result<()> {
while !buf.is_empty() {
match self.write(buf) {
Ok(0) => return Err(Error::new(ErrorKind::WriteZero,
"failed to write whole buffer")),
Ok(n) => buf = &buf[n..],
Err(ref e) if e.kind() == ErrorKind::Interrupted => {}
Err(e) => return Err(e),
}
}
Ok(())
}
...and a few more...
}
Run Code Online (Sandbox Code Playgroud)
任何想要实施的东西都Write 必须实施write和flush。提供了默认值write_all,但是您可以根据需要实现自己的默认值。
这是Vec<u8>实现方式,Write因此您可以“打印”到字节向量。
impl Write for Vec<u8> {
fn write(&mut self, buf: &[u8]) -> io::Result<usize> {
self.extend_from_slice(buf);
Ok(buf.len())
}
fn write_all(&mut self, buf: &[u8]) -> io::Result<()> {
self.extend_from_slice(buf);
Ok(())
}
fn flush(&mut self) -> io::Result<()> { Ok(()) }
}
Run Code Online (Sandbox Code Playgroud)
现在,当您编写需要输出内容的内容而不是决定是否应将其写入一个File或一个TcpStream(网络套接字)或其他内容时,您会说它必须具有Write特征。
fn display( out: Write ) {
out.write(...whatever...)
}
Run Code Online (Sandbox Code Playgroud)
Mixins是此版本的精简版。Mixins是注入到类中的方法的集合。就是这样 它们解决了多重继承和跨领域关注的问题,但解决的很少。接口没有正式的承诺,您只需调用方法并希望获得最好的接口即可。
Mixins在功能上大部分是等效的,但没有提供任何编译时检查以及特性所提供的高性能。
如果您熟悉mixin,那么特性将是组合功能的一种熟悉方式。定义接口的要求将是艰巨的,但是对于从JavaScript进入Rust的任何人来说,强类型将是一项艰巨的任务。
与JavaScript不同的是,mixins是一个简洁的插件,而traits是Rust的基本组成部分。它们使Rust成为强类型的,高性能的,非常安全的,而且非常灵活。特性使Rust可以对函数参数的有效性进行广泛的编译时检查,而无需强类型语言的传统限制。
Rust的许多核心部分都具有特征。std::io::Writer已经提到过。还有std::cmp::PartialEq哪个句柄==和!=。std::cmp::PartialOrd为>,>=,<和<=。std::fmt::Display关于如何打印东西{}。等等。
将特质视为 mixins 会让你远离而不是走向理解。Traits 从根本上讲是关于严格的类型系统,这对于母语是 JavaScript 的程序员来说是相当陌生的。
与大多数编程结构一样,特征足够灵活,可以以类似于 mixins 惯用方式的方式使用它们,但这与大多数其他程序员(包括标准库)使用特征的方式完全不同。
你应该将特质视为一种彻底的新奇事物。
| 归档时间: |
|
| 查看次数: |
833 次 |
| 最近记录: |