rust - 如何在期货链中使用 Result 类型中包含的套接字?
问题描述
我有以下来自 Tokio 文档的工作代码,我稍作修改:
// Task
let connection = io::read_exact(socket, buf_read)
.and_then(|(socket, buf_read)| {
println!("Do something with the received data...");
for b in &buf_read {
println!("{}", b);
}
// Write to the socket
let buf_write = vec![19; 30];
io::write_all(socket, buf_write)
})
.then(|res| {
println!("{:?}", res); // Just for testing
//Output: Ok((TcpStream, [19, 19, 19, ...]
println!("Send data...");
let buf_write = vec![18; 10]; // Fill the buffer with some data
//
//How to use the socket contained in res to write the data to the socket
//
Ok(())
});
请注意,这
res
是一个Result
包含原始套接字的。这允许我们在同一个套接字上对额外的读取或写入进行排序。
如何使用包含在套接字中的套接字Result
向套接字写入数据?
解决方案
请从重新阅读Rust 编程语言开始,特别是关于Recoverable Errors with Result的章节。然后重新阅读您正在使用的库的文档。
Future::then
,强调我的:
fn then<F, B>(self, f: F) -> Then<Self, B, F> where F: FnOnce(Result<Self::Item, Self::Error>) -> B, B: IntoFuture, Self: Sized,
链上一个未来何时完成的计算,将未来的结果传递给提供的闭包
f
。此函数可用于确保计算运行,而不管未来的结论如何。一旦未来完成,提供的关闭将被产生 。
Result
将此与您正在使用的其他功能进行对比Future::and_then
,强调我的:
fn and_then<F, B>(self, f: F) -> AndThen<Self, B, F> where F: FnOnce(Self::Item) -> B, B: IntoFuture<Error = Self::Error>, Self: Sized,
在这个成功解决后执行另一个未来。
此函数可用于将两个 future 链接在一起,并确保在两者都完成之前不会解析最终的 future。提供的闭包产生了这个未来的成功结果,并返回另一个可以转换为未来的值。
一种解决方案是仅通过以下方式成功处理它and_then
:
extern crate tokio; // 0.1.7
use tokio::{io, net::TcpStream, prelude::*};
fn example(socket: TcpStream, buf_read: Vec<u8>) {
io::read_exact(socket, buf_read)
.and_then(|(socket, buf_read)| {
let buf_write = vec![19; 30];
io::write_all(socket, buf_write)
}).and_then(|(socket, data)| {
let buf_write = vec![18; 10];
io::write_all(socket, buf_write)
});
// TODO: use future somehow
}
如果你想知道失败,那么你可以继续使用then
,但你必须以某种方式处理错误:
fn example(socket: TcpStream, buf_read: Vec<u8>) {
io::read_exact(socket, buf_read)
.and_then(|(socket, buf_read)| {
let buf_write = vec![19; 30];
io::write_all(socket, buf_write)
}).then(|res| match res {
Ok((socket, data)) => {
let buf_write = vec![18; 10];
io::write_all(socket, buf_write)
}
Err(e) => {
// Do something with the error and return another
// future that's type-compatible
unimplemented!()
},
});
// TODO: use future somehow
}
也可以看看:
推荐阅读
- php - 在 PHP 中将 MySQL 查询的结果操作成所需的 JSON 结构
- android - 从应用程序继承依赖版本到库模块
- java - 通过 retrofit2 调用与 Json Array 一起发送字段
- javascript - C3 条形图 - 自定义 X 轴标签
- android - 背景居中的带有图像/文本的按钮
- parameters - Hyperopt:定义依赖于其他参数的参数
- eclipse - 从 editorAction 迁移到 org.eclipse.ui.menus
- android - mvvm 的 Proguard 规则设置
- c# - 如何在 UI 线程中读取文件
- mysql - 仅在主条目经过认证时选择