@@ -898,51 +898,69 @@ fn add(x: int, y: int) -> int {
898
898
}
899
899
~~~~
900
900
901
- #### Diverging functions
902
901
903
- A special kind of function can be declared with a ` ! ` character where the
904
- output slot type would normally be. For example:
902
+ #### Generic functions
905
903
906
- ~~~~
907
- fn my_err(s: ~str) -> ! {
908
- log(info, s);
909
- fail;
904
+ A _ generic function_ allows one or more _ parameterized types_ to
905
+ appear in its signature. Each type parameter must be explicitly
906
+ declared, in an angle-bracket-enclosed, comma-separated list following
907
+ the function name.
908
+
909
+ ~~~~ {.xfail-test}
910
+ fn iter<T>(seq: ~[T], f: fn(T)) {
911
+ for seq.each |elt| { f(elt); }
912
+ }
913
+ fn map<T, U>(seq: ~[T], f: fn(T) -> U) -> ~[U] {
914
+ let mut acc = ~[];
915
+ for seq.each |elt| { acc.push(f(elt)); }
916
+ acc
910
917
}
911
918
~~~~
912
919
913
- We call such functions "diverging" because they never return a value to the
914
- caller. Every control path in a diverging function must end with a
915
- [ ` fail ` ] ( #fail-expressions ) or a call to another diverging function on every
916
- control path. The ` ! ` annotation does * not* denote a type. Rather, the result
917
- type of a diverging function is a special type called $\bot$ ("bottom") that
918
- unifies with any type. Rust has no syntax for $\bot$.
920
+ Inside the function signature and body, the name of the type parameter
921
+ can be used as a type name.
919
922
920
- It might be necessary to declare a diverging function because as mentioned
921
- previously, the typechecker checks that every control path in a function ends
922
- with a [ ` return ` ] ( #return-expressions ) or diverging expression. So, if ` my_err `
923
- were declared without the ` ! ` annotation, the following code would not
924
- typecheck:
923
+ When a generic function is referenced, its type is instantiated based
924
+ on the context of the reference. For example, calling the ` iter `
925
+ function defined above on ` [1, 2] ` will instantiate type parameter ` T `
926
+ with ` int ` , and require the closure parameter to have type
927
+ ` fn(int) ` .
925
928
926
- ~~~~
927
- # fn my_err(s: ~str) -> ! { fail }
929
+ Since a parameter type is opaque to the generic function, the set of
930
+ operations that can be performed on it is limited. Values of parameter
931
+ type can always be moved, but they can only be copied when the
932
+ parameter is given a [ ` copy ` bound] ( #type-kinds ) .
928
933
929
- fn f(i: int) -> int {
930
- if i == 42 {
931
- return 42;
932
- }
933
- else {
934
- my_err(~"Bad number!");
935
- }
936
- }
934
+ ~~~~
935
+ fn id<T: Copy>(x: T) -> T { x }
937
936
~~~~
938
937
939
- This will not compile without the ` ! ` annotation on ` my_err ` ,
940
- since the ` else ` branch of the conditional in ` f ` does not return an ` int ` ,
941
- as required by the signature of ` f ` .
942
- Adding the ` ! ` annotation to ` my_err ` informs the typechecker that,
943
- should control ever enter ` my_err ` , no further type judgments about ` f ` need to hold,
944
- since control will never resume in any context that relies on those judgments.
945
- Thus the return type on ` f ` only needs to reflect the ` if ` branch of the conditional.
938
+ Similarly, [ trait] ( #traits ) bounds can be specified for type
939
+ parameters to allow methods with that trait to be called on values
940
+ of that type.
941
+
942
+
943
+ #### Unsafe functions
944
+
945
+ Unsafe functions are those containing unsafe operations that are not contained in an [ ` unsafe ` block] ( #unsafe-blocks ) .
946
+
947
+ Unsafe operations are those that potentially violate the memory-safety guarantees of Rust's static semantics.
948
+ Specifically, the following operations are considered unsafe:
949
+
950
+ - Dereferencing a [ raw pointer] ( #pointer-types )
951
+ - Casting a [ raw pointer] ( #pointer-types ) to a safe pointer type
952
+ - Breaking the [ purity-checking rules] ( #pure-functions )
953
+ - Calling an unsafe function
954
+
955
+ ##### Unsafe blocks
956
+
957
+ A block of code can also be prefixed with the ` unsafe ` keyword,
958
+ to permit a sequence of unsafe operations in an otherwise-safe function.
959
+ This facility exists because the static semantics of a Rust are a necessary approximation of the dynamic semantics.
960
+ When a programmer has sufficient conviction that a sequence of unsafe operations is actually safe,
961
+ they can encapsulate that sequence (taken as a whole) within an ` unsafe ` block.
962
+ The compiler will consider uses of such code "safe", to the surrounding context.
963
+
946
964
947
965
#### Pure functions
948
966
@@ -1003,66 +1021,52 @@ function. So, to use `foldl` in a pure list length function that a pure function
1003
1021
could then use, we must use an ` unsafe ` block wrapped around the call to
1004
1022
` pure_foldl ` in the definition of ` pure_length ` .
1005
1023
1006
- #### Generic functions
1007
-
1008
- A _ generic function_ allows one or more _ parameterized types_ to
1009
- appear in its signature. Each type parameter must be explicitly
1010
- declared, in an angle-bracket-enclosed, comma-separated list following
1011
- the function name.
1012
-
1013
- ~~~~ {.xfail-test}
1014
- fn iter<T>(seq: ~[T], f: fn(T)) {
1015
- for seq.each |elt| { f(elt); }
1016
- }
1017
- fn map<T, U>(seq: ~[T], f: fn(T) -> U) -> ~[U] {
1018
- let mut acc = ~[];
1019
- for seq.each |elt| { acc.push(f(elt)); }
1020
- acc
1021
- }
1022
- ~~~~
1023
-
1024
- Inside the function signature and body, the name of the type parameter
1025
- can be used as a type name.
1026
1024
1027
- When a generic function is referenced, its type is instantiated based
1028
- on the context of the reference. For example, calling the ` iter `
1029
- function defined above on ` [1, 2] ` will instantiate type parameter ` T `
1030
- with ` int ` , and require the closure parameter to have type
1031
- ` fn(int) ` .
1025
+ #### Diverging functions
1032
1026
1033
- Since a parameter type is opaque to the generic function, the set of
1034
- operations that can be performed on it is limited. Values of parameter
1035
- type can always be moved, but they can only be copied when the
1036
- parameter is given a [ ` copy ` bound] ( #type-kinds ) .
1027
+ A special kind of function can be declared with a ` ! ` character where the
1028
+ output slot type would normally be. For example:
1037
1029
1038
1030
~~~~
1039
- fn id<T: Copy>(x: T) -> T { x }
1031
+ fn my_err(s: ~str) -> ! {
1032
+ log(info, s);
1033
+ fail;
1034
+ }
1040
1035
~~~~
1041
1036
1042
- Similarly, [ trait] ( #traits ) bounds can be specified for type
1043
- parameters to allow methods with that trait to be called on values
1044
- of that type.
1045
-
1046
- #### Unsafe functions
1047
-
1048
- Unsafe functions are those containing unsafe operations that are not contained in an [ ` unsafe ` block] ( #unsafe-blocks ) .
1037
+ We call such functions "diverging" because they never return a value to the
1038
+ caller. Every control path in a diverging function must end with a
1039
+ [ ` fail ` ] ( #fail-expressions ) or a call to another diverging function on every
1040
+ control path. The ` ! ` annotation does * not* denote a type. Rather, the result
1041
+ type of a diverging function is a special type called $\bot$ ("bottom") that
1042
+ unifies with any type. Rust has no syntax for $\bot$.
1049
1043
1050
- Unsafe operations are those that potentially violate the memory-safety guarantees of Rust's static semantics.
1051
- Specifically, the following operations are considered unsafe:
1044
+ It might be necessary to declare a diverging function because as mentioned
1045
+ previously, the typechecker checks that every control path in a function ends
1046
+ with a [ ` return ` ] ( #return-expressions ) or diverging expression. So, if ` my_err `
1047
+ were declared without the ` ! ` annotation, the following code would not
1048
+ typecheck:
1052
1049
1053
- - Dereferencing a [ raw pointer] ( #pointer-types )
1054
- - Casting a [ raw pointer] ( #pointer-types ) to a safe pointer type
1055
- - Breaking the [ purity-checking rules] ( #pure-functions )
1056
- - Calling an unsafe function
1050
+ ~~~~
1051
+ # fn my_err(s: ~str) -> ! { fail }
1057
1052
1058
- ##### Unsafe blocks
1053
+ fn f(i: int) -> int {
1054
+ if i == 42 {
1055
+ return 42;
1056
+ }
1057
+ else {
1058
+ my_err(~"Bad number!");
1059
+ }
1060
+ }
1061
+ ~~~~
1059
1062
1060
- A block of code can also be prefixed with the ` unsafe ` keyword,
1061
- to permit a sequence of unsafe operations in an otherwise-safe function.
1062
- This facility exists because the static semantics of a Rust are a necessary approximation of the dynamic semantics.
1063
- When a programmer has sufficient conviction that a sequence of unsafe operations is actually safe,
1064
- they can encapsulate that sequence (taken as a whole) within an ` unsafe ` block.
1065
- The compiler will consider uses of such code "safe", to the surrounding context.
1063
+ This will not compile without the ` ! ` annotation on ` my_err ` ,
1064
+ since the ` else ` branch of the conditional in ` f ` does not return an ` int ` ,
1065
+ as required by the signature of ` f ` .
1066
+ Adding the ` ! ` annotation to ` my_err ` informs the typechecker that,
1067
+ should control ever enter ` my_err ` , no further type judgments about ` f ` need to hold,
1068
+ since control will never resume in any context that relies on those judgments.
1069
+ Thus the return type on ` f ` only needs to reflect the ` if ` branch of the conditional.
1066
1070
1067
1071
1068
1072
#### Extern functions
0 commit comments