1- - Feature Name: convert_identity
1+ - Feature Name: ` convert_identity `
22- Start Date: 2018-01-19
33- RFC PR: (leave this empty)
44- Rust Issue: (leave this empty)
55
66# Summary
77[ summary ] : #summary
88
9- Adds an identity function ` pub const fn identity<T>(x: T) -> T { x } ` as
10- ` core::convert::identity ` . The function is also re-exported to
11- ` std::convert::identity ` as well as the prelude of
12- both libcore and libstd.
9+ Adds an identity function ` pub const fn identity<T>(x: T) -> T { x } `
10+ as ` core::convert::identity ` . The function is also re-exported to
11+ ` std::convert::identity ` .
1312
1413# Motivation
1514[ motivation ] : #motivation
@@ -61,6 +60,10 @@ let concatenated = iter_iter.flat_map(identity).collect::<Vec<_>>();
6160assert_eq! (vec! [1 , 3 , 4 , 5 , 6 ], concatenated );
6261```
6362
63+ While the standard library has recently added ` Iterator::flatten ` ,
64+ which you should use instead, to achieve the same semantics, similar situations
65+ are likely in the wild and the ` identity ` function can be used in those cases.
66+
6467### Using ` identity ` to keep the ` Some ` variants of an iterator of ` Option<T> `
6568
6669We can keep all the maybe variants by simply ` iter.filter_map(identity) ` .
@@ -93,8 +96,8 @@ Here are a few examples of the identity function being defined and used:
9396+ https://docs.rs/tool/0.2.0/tool/fn.id.html
9497+ https://github.com/hephex/api/blob/ef67b209cd88d0af40af10b4a9f3e0e61a5924da/src/lib.rs
9598
96- There's a smattering of more examples. To reduce duplication, it
97- should be provided in the standard library as a common place it is defined.
99+ There's a smattering of more examples. To reduce duplication,
100+ it should be provided in the standard library as a common place it is defined.
98101
99102## Precedent from other languages
100103
@@ -114,30 +117,6 @@ their standard libraries, among these are:
114117+ [ Agda] ( http://www.cse.chalmers.se/~nad/repos/lib/src/Function.agda )
115118+ [ Elm] ( http://package.elm-lang.org/packages/elm-lang/core/latest/Basics#identity )
116119
117- ## The case for inclusion in the prelude
118-
119- Let's compare the effort required, assuming that each letter
120- typed has a uniform cost wrt. effort.
121-
122- ``` rust
123- use std :: convert :: identity; iter . filter_map (identity )
124-
125- fn identity <T >(x : T ) -> T { x } iter . filter_map (identity )
126-
127- iter . filter_map (:: std :: convert :: identity )
128-
129- iter . filter_map (identity )
130- ```
131-
132- Comparing the length of these lines, we see that there's not much difference in
133- length when defining the function yourself or when importing or using an absolute
134- path. But the prelude-using variant is considerably shorter. To encourage the
135- use of the function, exporting to the prelude is therefore a good idea.
136-
137- In addition, there's an argument to be made from similarity to other things in
138- ` core::convert ` as well as ` drop ` all of which are in the prelude. This is
139- especially relevant in the case of ` drop ` which is also a trivial function.
140-
141120# Guide-level explanation
142121[ guide-level-explanation ] : #guide-level-explanation
143122
@@ -151,8 +130,7 @@ defines it as:
151130pub const fn identity <T >(x : T ) -> T { x }
152131```
153132
154- This function is also re-exported to ` std::convert::identity ` as well as
155- the prelude of both libcore and libstd.
133+ This function is also re-exported to ` std::convert::identity ` .
156134
157135It is important to note that the input ` x ` passed to the function is
158136moved since Rust uses move semantics by default.
@@ -162,7 +140,7 @@ moved since Rust uses move semantics by default.
162140
163141An identity function defined as ` pub const fn identity<T>(x: T) -> T { x } `
164142exists as ` core::convert::identity ` . The function is also re-exported as
165- ` std::convert::identity ` as well as the prelude of both libcore and libstd.
143+ ` std::convert::identity ` -
166144
167145Note that the identity function is not always equivalent to a closure
168146such as ` |x| x ` since the closure may coerce ` x ` into a different type
@@ -188,16 +166,46 @@ phrase. Meanwhile, `mem` does not relate to `identity` other than that both
188166deal with move semantics. Therefore, ` convert ` is the better choice. Including
189167it in ` mem ` is still an alternative, but as explained, it isn't fitting.
190168
191- The rationale for including this in the prelude has been previously
192- explained in the [ motivation] section. It is an alternative to not do that.
193- If the function is not in the prelude, the utility is so low that it may
194- be a better idea to not add the function at all.
195-
196169Naming the function ` id ` instead of ` identity ` is a possibility.
197170This name is however ambiguous with * "identifier"* and less clear
198171wherefore ` identifier ` was opted for.
199172
200173# Unresolved questions
201174[ unresolved ] : #unresolved-questions
202175
203- There are no unresolved questions.
176+ There are no unresolved questions.
177+
178+ # Possible future work
179+
180+ A previous iteration of this RFC proposed that the ` identity ` function
181+ should be added to prelude of both libcore and libstd.
182+ However, the library team decided that for the time being, it was not sold on
183+ this inclusion. As we gain usage experience with using this function,
184+ it is possible to revisit this in the future if the team chances its mind.
185+
186+ The section below details, for posterity,
187+ the argument for inclusion that was previously in the [ motivation] .
188+
189+ ## The case for inclusion in the prelude
190+
191+ Let's compare the effort required, assuming that each letter
192+ typed has a uniform cost with respect to effort.
193+
194+ ``` rust
195+ use std :: convert :: identity; iter . filter_map (identity )
196+
197+ fn identity <T >(x : T ) -> T { x } iter . filter_map (identity )
198+
199+ iter . filter_map (:: std :: convert :: identity )
200+
201+ iter . filter_map (identity )
202+ ```
203+
204+ Comparing the length of these lines, we see that there's not much difference in
205+ length when defining the function yourself or when importing or using an absolute
206+ path. But the prelude-using variant is considerably shorter. To encourage the
207+ use of the function, exporting to the prelude is therefore a good idea.
208+
209+ In addition, there's an argument to be made from similarity to other things in
210+ ` core::convert ` as well as ` drop ` all of which are in the prelude. This is
211+ especially relevant in the case of ` drop ` which is also a trivial function.
0 commit comments