| # Functions |
| |
| Ignoring [elision], function signatures with lifetimes have a few constraints: |
| |
| * any reference *must* have an annotated lifetime. |
| * any reference being returned *must* have the same lifetime as an input or |
| be `static`. |
| |
| Additionally, note that returning references without input is banned if it |
| would result in returning references to invalid data. The following example shows |
| off some valid forms of functions with lifetimes: |
| |
| ```rust,editable |
| // One input reference with lifetime `'a` which must live |
| // at least as long as the function. |
| fn print_one<'a>(x: &'a i32) { |
| println!("`print_one`: x is {}", x); |
| } |
| |
| // Mutable references are possible with lifetimes as well. |
| fn add_one<'a>(x: &'a mut i32) { |
| *x += 1; |
| } |
| |
| // Multiple elements with different lifetimes. In this case, it |
| // would be fine for both to have the same lifetime `'a`, but |
| // in more complex cases, different lifetimes may be required. |
| fn print_multi<'a, 'b>(x: &'a i32, y: &'b i32) { |
| println!("`print_multi`: x is {}, y is {}", x, y); |
| } |
| |
| // Returning references that have been passed in is acceptable. |
| // However, the correct lifetime must be returned. |
| fn pass_x<'a, 'b>(x: &'a i32, _: &'b i32) -> &'a i32 { x } |
| |
| //fn invalid_output<'a>() -> &'a String { &String::from("foo") } |
| // The above is invalid: `'a` must live longer than the function. |
| // Here, `&String::from("foo")` would create a `String`, followed by a |
| // reference. Then the data is dropped upon exiting the scope, leaving |
| // a reference to invalid data to be returned. |
| |
| fn main() { |
| let x = 7; |
| let y = 9; |
| |
| print_one(&x); |
| print_multi(&x, &y); |
| |
| let z = pass_x(&x, &y); |
| print_one(z); |
| |
| let mut t = 3; |
| add_one(&mut t); |
| print_one(&t); |
| } |
| ``` |
| |
| ### See also: |
| |
| [Functions][fn] |
| |
| [fn]: ../../fn.md |
| |
| [elision]: elision.md |