Rust by Example — страница 53 из 66

String or character literal delimiters occuring within a literal must be escaped: "\"", '\''.

fn main() {

// You can use escapes to write bytes by their hexadecimal values...

let byte_escape = "I'm writing \x52\x75\x73\x74!";

println!("What are you doing\x3F (\\x3F means ?) {}", byte_escape);

// ...or Unicode code points.

let unicode_codepoint = "\u{211D}";

let character_name = "\"DOUBLE-STRUCK CAPITAL R\"";

println!("Unicode character {} (U+211D) is called {}",

unicode_codepoint, character_name );

let long_string = "String literals

can span multiple lines.

The linebreak and indentation here ->\

<- can be escaped too!";

println!("{}", long_string);

}

הההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההה

XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX

Sometimes there are just too many characters that need to be escaped or it's just much more convenient to write a string out as-is. This is where raw string literals come into play.

fn main() {

let raw_str = r"Escapes don't work here: \x3F \u{211D}";

println!("{}", raw_str);

// If you need quotes in a raw string, add a pair of #s

let quotes = r#"And then I said: "There is no escape!""#;

println!("{}", quotes);

// If you need "# in your string, just use more #s in the delimiter.

// There is no limit for the number of #s you can use.

let longer_delimiter = r###"A string with "# in it. And even "##!"###;

println!("{}", longer_delimiter);

}

הההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההה

XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX

Want a string that's not UTF-8? (Remember, str and String must be valid UTF-8). Or maybe you want an array of bytes that's mostly text? Byte strings to the rescue!

use std::str;

fn main() {

// Note that this is not actually a `&str`

let bytestring: &[u8; 21] = b"this is a byte string";

// Byte arrays don't have the `Display` trait, so printing them is a bit limited

println!("A byte string: {:?}", bytestring);

// Byte strings can have byte escapes...

let escaped = b"\x52\x75\x73\x74 as bytes";

// ...but no unicode escapes

// let escaped = b"\u{211D} is not allowed";

println!("Some escaped bytes: {:?}", escaped);

// Raw byte strings work just like raw strings

let raw_bytestring = br"\u{211D} is not escaped here";

println!("{:?}", raw_bytestring);

// Converting a byte array to `str` can fail

if let Ok(my_str) = str::from_utf8(raw_bytestring) {

println!("And the same as text: '{}'", my_str);

}

let _quotes = br#"You can also use "fancier" formatting, \

like with normal raw strings"#;

// Byte strings don't have to be UTF-8

let shift_jis = b"\x82\xe6\x82\xa8\x82\xb1\x82\xbb"; // "ようこそ" in SHIFT-JIS

// But then they can't always be converted to `str`

match str::from_utf8(shift_jis) {

Ok(my_str) => println!("Conversion successful: '{}'", my_str),

Err(e) => println!("Conversion failed: {:?}", e),

};

}

הההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההה

XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX

For conversions between character encodings check out the encoding crate.

A more detailed listing of the ways to write string literals and escape characters is given in the 'Tokens' chapter of the Rust Reference.

Option

Sometimes it's desirable to catch the failure of some parts of a program instead of calling panic!; this can be accomplished using the Option enum.

The Option enum has two variants:

   • None, to indicate failure or lack of value, and

   • Some(value), a tuple struct that wraps a value with type T.

// An integer division that doesn't `panic!`

fn checked_division(dividend: i32, divisor: i32) -> Option {

if divisor == 0 {

// Failure is represented as the `None` variant

None

} else {

// Result is wrapped in a `Some` variant

Some(dividend / divisor)

}

}

// This function handles a division that may not succeed

fn try_division(dividend: i32, divisor: i32) {

// `Option` values can be pattern matched, just like other enums

match checked_division(dividend, divisor) {

None => println!("{} / {} failed!", dividend, divisor),

Some(quotient) => {

println!("{} / {} = {}", dividend, divisor, quotient)

},

}

}

fn main() {

try_division(4, 2);

try_division(1, 0);

// Binding `None` to a variable needs to be type annotated

let none: Option = None;

let _equivalent_none = None::;

let optional_float = Some(0f32);

// Unwrapping a `Some` variant will extract the value wrapped.

println!("{:?} unwraps to {:?}", optional_float, optional_float.unwrap());

// Unwrapping a `None` variant will `panic!`

println!("{:?} unwraps to {:?}", none, none.unwrap());

}

הההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההההה

XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXX