Description
impl From<T> for Option<T> {
fn from(val: T) -> Self {
Option::Some(val)
}
}
This is a trivial impl and I think it would help ergonomics in certain areas of API design. As an example, consider a method on a fictional I/O wrapper for setting a timeout:
struct Socket;
impl Socket {
// Set the timeout, in seconds. Removes timeout if `None`.
fn set_timeout<T: Into<Option<u64>>(&mut self, timeout: T) { /* .. */ }
}
This can be called in both of the following forms without needing separate methods for u64
and Option<u64>
:
let mut socket = Socket;
socket.set_timeout(3600);
socket.set_timeout(None);
Currently, if this API wanted to take an Option<u64>
, it would have to be invariant over it:
fn set_timeout(&mut self, timeout: Option<u64>);
Requiring Some
everywhere:
socket.set_timeout(Some(3600));
I think the above is much cleaner.
There are existing APIs such as the following:
http://doc.rust-lang.org/nightly/std/net/struct.UdpSocket.html#method.set_read_timeout
which I think could be migrated relatively seamlessly. I think the only breakage would be if someone was referring to them by UFCS, so the addition of a type parameter would break resolution (maybe). A Crater run would probably help here.
Otherwise, I don't see much as far as downsides go, except maybe some brief confusion for newbies. However, I don't think it would take them long to realize, "Oh! It can take u64
or Option<u64>
. Cool!" Then it's just another neat little feature of Rust. I don't think accidental conversions would be a problem, either.