@@ -21,7 +21,7 @@ With the placeholder syntax used in discussions so far,
21
21
abstract return types would be used roughly like this:
22
22
23
23
``` rust
24
- fn foo (n : u32 ) -> impl Iterator <Item = u32 > {
24
+ fn foo (n : u32 ) -> impl Iterator <Item = u32 > {
25
25
(0 .. n ). map (| x | x * 100 )
26
26
}
27
27
// ^ behaves as if it had return type Map<Range<u32>, Closure>
@@ -30,7 +30,6 @@ fn foo(n: u32) -> impl Iterator<Item=u32> {
30
30
for x in foo (10 ) {
31
31
// x = 0, 100, 200, ...
32
32
}
33
-
34
33
```
35
34
36
35
# Background
@@ -61,10 +60,10 @@ its motivation and some other parts of its text below.
61
60
62
61
In today's Rust, you can write a function signature like
63
62
64
- ```` rust
65
- fn consume_iter_static <I : Iterator <u8 >>(iter : I )
66
- fn consume_iter_dynamic (iter : Box <Iterator <u8 >>)
67
- ````
63
+ ``` rust
64
+ fn consume_iter_static <I : Iterator <Item = u8 >>(iter : I )
65
+ fn consume_iter_dynamic (iter : Box <Iterator <Item = u8 >>)
66
+ ```
68
67
69
68
In both cases , the function does not depend on the exact type of the argument .
70
69
The type is held " abstract" , and is assumed only to satisfy a trait bound .
@@ -78,15 +77,15 @@ The type is held "abstract", and is assumed only to satisfy a trait bound.
78
77
79
78
On the other hand , while you can write
80
79
81
- ```` rust
82
- fn produce_iter_dynamic () -> Box <Iterator <u8 >>
83
- ````
80
+ ```rust
81
+ fn produce_iter_dynamic () -> Box <Iterator <Item = u8 >>
82
+ ```
84
83
85
84
you _cannot_ write something like
86
85
87
- ```` rust
88
- fn produce_iter_static () -> Iterator <u8 >
89
- ````
86
+ ```rust
87
+ fn produce_iter_static () -> Iterator <Item = u8 >
88
+ ```
90
89
91
90
That is , in today 's Rust , abstract return types can only be written using trait
92
91
objects , which can be a significant performance penalty . This RFC proposes
@@ -105,15 +104,15 @@ Here are some problems that unboxed abstract types solve or mitigate:
105
104
type , when the API should really only promise a trait bound . For example , a
106
105
function returning `Rev <Splits <'a , u8 >>` is revealing exactly how the iterator
107
106
is constructed , when the function should only promise that it returns _some_
108
- type implementing `Iterator <u8 >`. Using newtypes / structs with private fields
107
+ type implementing `Iterator <Item = u8 >`. Using newtypes / structs with private fields
109
108
helps , but is extra work . Unboxed abstract types make it as easy to promise only
110
109
a trait bound as it is to return a concrete type .
111
110
112
111
* _Complex types_ . Use of iterators in particular can lead to huge types :
113
112
114
- ```` rust
115
- Chain <Map <'a , (int , u8 ), u16 , Enumerate <Filter <'a , u8 , vec :: MoveItems <u8 >>>>, SkipWhile <'a , u16 , Map <'a , & u16 , u16 , slice :: Items <u16 >>>>
116
- ````
113
+ ```rust
114
+ Chain <Map <'a , (i32 , u8 ), u16 , Enumerate <Filter <'a , u8 , vec :: MoveItems <u8 >>>>, SkipWhile <'a , u16 , Map <'a , & u16 , u16 , slice :: Items <u16 >>>>
115
+ ```
117
116
118
117
Even when using newtypes to hide the details , the type still has to be written
119
118
out , which can be very painful . Unboxed abstract types only require writing the
0 commit comments