-
Notifications
You must be signed in to change notification settings - Fork 13.3k
Update io iterators to produce IoResults #12414
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Conversation
This is part of a discussion on the ML and as part of #12368. At this point, there doesn't appear to be a generally agreed upon consensus regarding a solution or even that there is a problem that needs a solution. So, this should not be merged until that discussion concludes and only if this is the agreed upon solution. However, in the meantime, this is a concrete proposal that can be analyzed. Discussion of the general issue should probably continue on #12368. |
This seems like a good compromise between the competing interests to me. Some thoughts:
All-in-all, I'd like to reduce your example down to: use std::io;
fn main() {
for line in io::stdin().lines().fail_on_error() {
println!("{}", line);
}
} |
I don't love the name either, but I didn't have any better ideas. I didn't implement it as a method on I didn't implement it as a function, because I thought that: for line in io::fail_on_error(io::stdin().lines()) didn't read really well. |
I update the PR since I had some changes sitting around necessary to make everything compile. I also renamed the extension trait to IteratorIoExt since the original name, IoIterator, seemed a bit misleading since it wasn't actually an Iterator. If it were decided to merge this, I'd like to squash a few of these things first. |
Closing due to a lack of activity, but feel free to reopen with a rebase! |
Rebased against master, passes make check. I'd mostly left this PR alone since I opened it in response to a mailing list / Issue discussion and I was waiting to see if that discussion was going to reach some sort of consensus. I haven't seen any further developments in that conversation, however. I've made a few changes:
With the change to make stdin() buffered and with these changes, the example program that was being discussed now looks like this: use std::io;
use std::io::util::IteratorExtensions;
fn main() {
for line in io::stdin().lines().fail_on_error() {
print!("received: {}", line);
}
} So, as it currently stands, it still requires the extra for x in file1.lines().fail_on_error().chain(file2.lines().fail_on_error()) { ... } However, with for x in file1.lines().chain(file2.lines()).fail_on_error() { ... } Which I think reads a bit nicer. Also, I think its a bit more user-friendly - I haven't come up with a better name for |
Reopening at @DaGenix's request. |
The iterator extension traits seem difficult to discover, and I'm coming around to think that they may not be necessary at all. We have the I'm still a bit wary of whether this is the direction that we want to go in, the whole point is to make use std::io;
fn main() {
for line in io::stdin().lines() {
print!("received: {}", line.unwrap());
}
} |
I agree that discoverability is an issue. Putting the extension in the prelude would somewhat address the issue, however, then there is a magic method that shows up somewhat out of nowhere. Anyway, I'm also of the opinion that the extension trait isn't necessary. In my opinion what is important is that all of the APIs in the standard library should be a) correct and b) easy to use, in that order. If an API isn't correct, ease of use becomes a bad thing since it will just spread the problem farther, faster, and with a lower chance that people look up the documentation. Ignoring errors makes the particular 5 line program under discussion look mildly nicer; however, it also makes the API impossible to use in anything non-trivial - if I want to iterate over the lines of a file and I also want to handle errors, where's my lines() method? What I'm getting at is I think we should make these iterators correct and consistent first and then try to figure out if there is some nice sugar to make that particular example prettier. I've rebased the PR to remove the extension traits and to just change the iterators to produce IoResults. |
One thing I noticed while making the changes in this PR is that one of the examples in the use std::io::BufferedReader;
use std::io::File;
let path = Path::new("message.txt");
let mut file = BufferedReader::new(File::open(&path));
for line in file.lines() {
print!("{}", line);
} The issue is that |
@@ -15,15 +15,17 @@ | |||
// FIXME: Not sure how this should be structured | |||
// FIXME: Iteration should probably be considered separately | |||
|
|||
use prelude::*; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
We've been trying to prevent imports of the prelude throughout libstd
, it often leads to obscure resolve errors.
Just two minor nits, then I think this is good for merging. |
Most IO related functions return an IoResult so that the caller can handle failure in whatever way is appropriate. However, the `lines`, `bytes`, and `chars` iterators all supress errors. This means that code that needs to handle errors can't use any of these iterators. All three of these iterators were updated to produce IoResults. Fixes rust-lang#12368
Rebased to address your comments |
…crichton Most IO related functions return an IoResult so that the caller can handle failure in whatever way is appropriate. However, the `lines`, `bytes`, and `chars` iterators all supress errors. This means that code that needs to handle errors can't use any of these iterators. All three of these iterators were updated to produce IoResults. Fixes #12368
fix: float display impl should solve rust-lang#12414
Most IO related functions return an IoResult so that the caller can handle failure in whatever way is appropriate. However, the
lines
,bytes
, andchars
iterators all supress errors. This means that code that needs to handle errors can't use any of these iterators. All three of these iterators were updated to produce IoResults.Fixes #12368