我如何告诉 Rust 中的 std::io::copy 停止阅读并完成写作?
How do I tell std::io::copy in Rust to stop reading and finish up writing?
我正在通过 Rust 直接下载 MP3 音频流。由于这个流是不确定的,我希望能够提前取消它以保存我目前下载的内容。目前,我通过按 CTRL + C 来停止程序。这会生成一个 stream.mp3 文件,然后我可以播放和收听,虽然这可行,但并不理想。
给定以下代码,我如何以编程方式提前停止 io::copy()
并让它在不终止整个程序的情况下保存文件?
extern crate reqwest;
use std::io;
use std::fs::File;
// Note that this is a direct link to the stream, not a webpage with HTML and a stream
const STREAM_URL: &str = "http://path.to/stream";
fn main() {
let mut response = reqwest::get(STREAM_URL)
.expect("Failed to request mp3 stream");
let mut output = File::create("stream.mp3")
.expect("Failed to create file!");
io::copy(&mut response, &mut output)
.expect("Failed to copy mp3 stream to file");
}
正如评论所说,io::copy
是一种方便的功能,可以完整读取 Reader
并将其内容写入 Writer
而不会在两者之间停止;它用于当您 不 关心中间状态但只想将整个内容从 reader 发送给作者时。
如果您只想要 response
的前几 Kb,您可以使用 io::Read::take,它将 Reader
限制为您指定的任何限制。它将 return 一个新的 Reader
,您可以将其传递给 io::copy
。
是的,您可以在任意位置剪切 MP3 文件。它是一种帧格式,虽然您很可能会破坏最后一帧,但实际上所有 mp3 解码器都能够处理这种情况。
有点像
// `Read` needs to be in scope, so .take() is available on a `io::Read`
use std::io::Read;
use std::io;
use std::fs::File;
fn main() {
let mut response = reqwest::get(STREAM_URL)
.expect("Failed to request mp3 stream")
.take(100*1024); // Since `Response` is `Read`, we can `take` from it.
let mut output = File::create("stream.mp3")
.expect("Failed to create file!");
// `response` is a limited reader, so it will only read 100kb before
// returning EOF, signaling a successful completion to `copy`.
io::copy(&mut response, &mut output)
.expect("Failed to copy mp3 stream to file");
}
我正在通过 Rust 直接下载 MP3 音频流。由于这个流是不确定的,我希望能够提前取消它以保存我目前下载的内容。目前,我通过按 CTRL + C 来停止程序。这会生成一个 stream.mp3 文件,然后我可以播放和收听,虽然这可行,但并不理想。
给定以下代码,我如何以编程方式提前停止 io::copy()
并让它在不终止整个程序的情况下保存文件?
extern crate reqwest;
use std::io;
use std::fs::File;
// Note that this is a direct link to the stream, not a webpage with HTML and a stream
const STREAM_URL: &str = "http://path.to/stream";
fn main() {
let mut response = reqwest::get(STREAM_URL)
.expect("Failed to request mp3 stream");
let mut output = File::create("stream.mp3")
.expect("Failed to create file!");
io::copy(&mut response, &mut output)
.expect("Failed to copy mp3 stream to file");
}
正如评论所说,io::copy
是一种方便的功能,可以完整读取 Reader
并将其内容写入 Writer
而不会在两者之间停止;它用于当您 不 关心中间状态但只想将整个内容从 reader 发送给作者时。
如果您只想要 response
的前几 Kb,您可以使用 io::Read::take,它将 Reader
限制为您指定的任何限制。它将 return 一个新的 Reader
,您可以将其传递给 io::copy
。
是的,您可以在任意位置剪切 MP3 文件。它是一种帧格式,虽然您很可能会破坏最后一帧,但实际上所有 mp3 解码器都能够处理这种情况。
有点像
// `Read` needs to be in scope, so .take() is available on a `io::Read`
use std::io::Read;
use std::io;
use std::fs::File;
fn main() {
let mut response = reqwest::get(STREAM_URL)
.expect("Failed to request mp3 stream")
.take(100*1024); // Since `Response` is `Read`, we can `take` from it.
let mut output = File::create("stream.mp3")
.expect("Failed to create file!");
// `response` is a limited reader, so it will only read 100kb before
// returning EOF, signaling a successful completion to `copy`.
io::copy(&mut response, &mut output)
.expect("Failed to copy mp3 stream to file");
}