-
Notifications
You must be signed in to change notification settings - Fork 12.9k
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
Tracking issue for Zero
/One
/iter_arith
stabilization
#27739
Comments
Those traits would be really useful for generic arithmetics, I look forward to them being stabilized. Also, I have some ideas for traits that would pair up with those nicely, e.g.: |
I would like to see these are stabilized. They are really useful and simple enough to have a position in |
Nominating for 1.6 discussion. |
I have multiple times tried to use Please stabilize |
There is an open issue with iterator sum and product regarding type inference / default type parameter fallback (#25094) I'm not sure how this impacts stabilization. |
Unfortunately the libs team didn't have time to decided on this in the triage meeting, so this won't enter FCP this cycle. |
I'd like to nominate at least |
As a general point, these traits don't necessarily cover everything one might want for non-primitives. In particular, Additionally, for other types, it may not make sense to just ask for |
I agree that precision is important for big-floats, but I don't think that the notion of precision belongs in Zero. Something like |
If I’m grepping correctly,
Since we’ve already decided to reduce the scope of (Edited to remove truncated paragraph, it was the same as the previous one.) |
🔔 This issue is now entering its final comment period for stabilization 🔔 At the libs triage meeting we discussed that we may want to somewhat aggresively pursue stabilization of the methods here, and if it comes to it we can punt on stabilizing the traits involves (as we've done with other APIs in the past). @aturon however I believe would like to discuss stabilizing the tl;dr; This FCP is primarily for stabilizing the |
The type parameter default should be removed before stabilization, it has no effect, and the lang team seems to unfortunately doubt the future of the feature altogether. |
@SimonSapin Your comment was cut short, but I think I agree. Zero and One are out of place as the only numeric traits in libstd. That said, it's good for everyone if One and Zero are either stabilized or removed. Unstable limbo just leads to the tricky conflicts of std's Zero vs num's Zero. |
|
@bluss Good catch. For the record, the difference is that Given that we want a direct connection between e.g. That issue aside, the only real question with I agree with @SimonSapin's assessment. I also think that these traits are relatively harmless -- they are effectively specialized versions of So overall, I think I'm 👍 on stabilization of all items in question (modulo adjusting to match the |
If we have concerns about future compatibility with more robust numeric trait hierarchies, we can always make these traits specifically for |
How about, in trait Sum: Add<Rhs=Self> {
/// Sum of an empty sequence, i.e. "zero".
fn neutral_element() -> Self;
}
trait Product: Mul<Rhs=Self> {
/// Product of an empty sequence, i.e. "one".
fn neutral_element() -> Self;
} |
@aturon I wasn't even aware of the differences in their definition. What I meant by num's Zero and std's Zero are not compatible, is simply that if my crate requires |
@SimonSapin @sfackler I'm not sure I see the appeal of defining these traits so narrowly, or in @bluss I see. So, in general, we'd like to handle this by changing |
Ah one question we did have when discussing this was what to do about overflow. We no longer really have the convenience of "overflows as if you wrote the code locally" so we'll have to define semantics one way or another. |
I’ve just realize that this design would allow implementations to use an algorithm different from https://docs.python.org/3/library/math.html#math.fsum But is this desirable? It looks like that algorithm allocates memory, so there’s a run-time cost to get that accuracy. This may be a trade-off better left to users to decide. Python itself provides So I think such an accurate sum would be better as a separate API, and it could be on crates.io at least at first. I think that the impls in std of theses traits should simply use This also deals with overflow semantics, doesn’t it? Leave it per-impl, but give a recommendation (and follow it in std). |
You can get a significant precision win with just one extra float for which no heap allocation is required (at the cost of more arithmetic operations). But I wouln’t expect the standard library |
Someone did actually mention the overflow problem. I currently have an open issue at the rfcs repo about checked (and the like) methods for @cuviper suggested:
So we had something like: // within Iterator
fn sum<S>(self) -> Option<S>
where S: Add<Self::Item, Output=S> This would also solve the overflowing problem (although it could return The If for any reason you want to not use the |
I would expect Using I don't see a huge difference between Simon's last suggestion and my adjustment to his earlier suggestion in terms of how much special-purpose code needs to get added to the standard library. Is there another possibility, to use a trait-based fold design? trait Foldable<T, R> {
fn initial() -> R;
fn fold(x: T, r: R) -> Option<R>;
} This may allow implementations like use fold_impls::Sum;
fn main() {
let v = vec![1, 2, 3, 4];
println!("Sum: {}", v.fold_with(Sum).unwrap());
} |
Sorry, no I meant something different and accidentally hit Ctrl while trying to get a newline somewhere, sorry for that. First of all, current feature gated This also means that your fn fold_with<T,R>(&mut self, fold_t: &Foldable<T, R>) -> Option<R> Should actually take ownership of the value. Edit: current fold looks like this: fn fold<B, F>(self, init: B, f: F) -> B where F: FnMut(B, Self::Item) -> B { ... } Furthermore, could you please explain what advantages your Just Sorry, it might just be me not seeing the point there. |
I'd be happy if you added the Also how would that:
work if you take fn fold_with<T,R>(&mut self, fold_t: &Foldable<T, R>) -> Option<R> Wouldn't it be more like extern crate something;
fn main() {
let v: Vec<usize> = vec![1,2,3];
// just to have some unified way to get such a structure `new` is used
// because sometimes there might be an internal state to hold (for caching, or whatever reasons)
// if this was not desirable one could simply have `let sum = something::sum::Sum;` I think
let sum = something::sum::Sum::new();
println!("Sum: {}", v.iter().fold_with(&sum).unwrap());
} Edit: I just saw you corrected the |
Thanks for your comments. @benaryorg The reference to Maybe you're right that an object The potential advantage of the trait is to specify two related things together (both functions of the same trait impl), but maybe it's not worth it. |
Note that at least in the past when the libs team has discussed these APIs the thought is that if we don't have the ergonomics that we have today then the methods probably aren't worth it. The Along those lines I don't think we want to introduce new methods like The thinking is that using a |
I'll stick to @SimonSapin's solution then. One can still check for overflows by invoking v.iter().fold(Some(0),|a,&b|a.and_then(|a: usize|a.checked_add(b))) |
Just to add another use-case of While |
I agree wholeheartedly with @alexcrichton -- at this point, with this tracking issue, we should focus on landing support for ergonomic |
The libs team discussed this issue during triage yesterday and the decision was to stabilize. We realize that the FCP for this issue was pretty short, however, so please comment with any objections you might have! We're very willing to backport an un-stabilization for the few APIs we have this cycle. Specifically, we're thinking of stabilizing the |
I feel that something monoid-identity like might not be a good match for What is really desired for |
@alexcrichton So, stabilizing without any of the API changes proposed here? |
@SimonSapin No, we're moving to the |
Although the set of APIs being stabilized this release is relatively small, the trains keep going! Listed below are the APIs in the standard library which have either transitioned from unstable to stable or those from unstable to deprecated. Stable * `BTreeMap::{append, split_off}` * `BTreeSet::{append, split_off}` * `Cell::get_mut` * `RefCell::get_mut` * `BinaryHeap::append` * `{f32, f64}::{to_degrees, to_radians}` - libcore stabilizations mirroring past libstd stabilizations * `Iterator::sum` * `Iterator::product` Deprecated * `{f32, f64}::next_after` * `{f32, f64}::integer_decode` * `{f32, f64}::ldexp` * `{f32, f64}::frexp` * `num::One` * `num::Zero` Added APIs (all unstable) * `iter::Sum` * `iter::Product` * `iter::Step` - a few methods were added to accomodate deprecation of One/Zero Removed APIs * `From<Range<T>> for RangeInclusive<T>` - everything about `RangeInclusive` is unstable Closes rust-lang#27739 Closes rust-lang#27752 Closes rust-lang#32526 Closes rust-lang#33444 Closes rust-lang#34152 cc rust-lang#34529 (new tracking issue)
std: Stabilize APIs for the 1.11.0 release Although the set of APIs being stabilized this release is relatively small, the trains keep going! Listed below are the APIs in the standard library which have either transitioned from unstable to stable or those from unstable to deprecated. Stable * `BTreeMap::{append, split_off}` * `BTreeSet::{append, split_off}` * `Cell::get_mut` * `RefCell::get_mut` * `BinaryHeap::append` * `{f32, f64}::{to_degrees, to_radians}` - libcore stabilizations mirroring past libstd stabilizations * `Iterator::sum` * `Iterator::product` Deprecated * `{f32, f64}::next_after` * `{f32, f64}::integer_decode` * `{f32, f64}::ldexp` * `{f32, f64}::frexp` * `num::One` * `num::Zero` Added APIs (all unstable) * `iter::Sum` * `iter::Product` * `iter::Step` - a few methods were added to accomodate deprecation of One/Zero Removed APIs * `From<Range<T>> for RangeInclusive<T>` - everything about `RangeInclusive` is unstable Closes #27739 Closes #27752 Closes #32526 Closes #33444 Closes #34152 cc #34529 (new tracking issue)
The `num::One` and `num::Zero` traits were removed on nightly. See the tracking issue rust-lang/rust#27739
We currently have
Zero
andOne
traits that are meant to work withAdd
andMul
and support iterator operations likesum
, as well as the currentstep_by
API.It would be good to have a more comprehensive vision for this kind of trait before stabilization; an RFC would be ideal.
The text was updated successfully, but these errors were encountered: