* Digits of binary and octal literals are [lexed more eagerly][lex] to
improve error messages and macro behavior. For example, `0b1234` is
now lexed as `0b1234` instead of two tokens, `0b1` and `234`.
-* Trait bounds [are always invariant][inv], eleminating the need for
+* Trait bounds [are always invariant][inv], eliminating the need for
the `PhantomFn` and `MarkerTrait` lang items, which have been
removed.
* ["-" is no longer a valid character in crate names][cr], the `extern crate
Version 1.0.0-alpha.2 (February 2015)
--------------------------------------
+=====================================
* ~1300 changes, numerous bugfixes
[ufcs-rfc]: https://github.com/rust-lang/rfcs/blob/master/text/0132-ufcs.md
[un]: https://github.com/rust-lang/rust/pull/22256
+
Version 1.0.0-alpha (January 2015)
-----------------------------------
+==================================
* ~2400 changes, numerous bugfixes
[trpl]: http://doc.rust-lang.org/book/index.html
[rbe]: http://rustbyexample.com/
+
Version 0.12.0 (October 2014)
------------------------------
+=============================
* ~1900 changes, numerous bugfixes
* Official Rust binaries on Linux are more compatible with older
kernels and distributions, built on CentOS 5.10.
+
Version 0.11.0 (July 2014)
--------------------------
+==========================
* ~1700 changes, numerous bugfixes
* Error message related to non-exhaustive match expressions have been
greatly improved.
+
Version 0.10 (April 2014)
--------------------------
+=========================
* ~1500 changes, numerous bugfixes
* search works across crates that have been rendered to the same output
directory.
+
Version 0.9 (January 2014)
---------------------------
+==========================
* ~1800 changes, numerous bugfixes
* `rustc` adds a `--dep-info` flag for communicating dependencies to
build tools.
+
Version 0.8 (September 2013)
---------------------------
+============================
* ~2200 changes, numerous bugfixes
* A new documentation backend, rustdoc_ng, is available for use. It is
still invoked through the normal `rustdoc` command.
+
Version 0.7 (July 2013)
------------------------
+=======================
* ~2000 changes, numerous bugfixes
* Various improvements to rustdoc.
* Improvements to rustpkg (see the detailed release notes).
+
Version 0.6 (April 2013)
-------------------------
+========================
* ~2100 changes, numerous bugfixes
* Rust code may be embedded in foreign code under limited circumstances
* Inline assembler supported by new asm!() syntax extension.
+
Version 0.5 (December 2012)
----------------------------
+===========================
* ~900 changes, numerous bugfixes
* Added a preliminary REPL, `rusti`
* License changed from MIT to dual MIT/APL2
+
Version 0.4 (October 2012)
---------------------------
+==========================
* ~2000 changes, numerous bugfixes
Rust-based (visitor) code
* All hash functions and tables converted to secure, randomized SipHash
+
Version 0.3 (July 2012)
-------------------------
+========================
* ~1900 changes, numerous bugfixes
* Tool improvements
* Cargo automatically resolves dependencies
+
Version 0.2 (March 2012)
--------------------------
+=========================
* >1500 changes, numerous bugfixes
* Merged per-platform std::{os*, fs*} to core::{libc, os}
* Extensive cleanup, regularization in libstd, libcore
+
Version 0.1 (January 20, 2012)
--------------------------------
+===============================
* Most language features work, including:
* Unique pointers, unique closures, move semantics
Rust supports benchmark tests, which can test the performance of your
code. Let's make our `src/lib.rs` look like this (comments elided):
-```{rust,ignore}
+```rust,ignore
#![feature(test)]
extern crate test;
compiler might recognize that some calculation has no external effects and
remove it entirely.
-```{rust,ignore}
+```rust,ignore
#![feature(test)]
extern crate test;
For most types, when you want to take an owned or borrowed type, a `&T` is
enough. But one area where `Borrow` is effective is when there’s more than one
-kind of borrowed value. Slices are an area where this is especially true: you
-can have both an `&[T]` or a `&mut [T]`. If we wanted to accept both of these
-types, `Borrow` is up for it:
+kind of borrowed value. This is especially true of references and slices: you
+can have both an `&T` or a `&mut T`. If we wanted to accept both of these types,
+`Borrow` is up for it:
-```
+```rust
use std::borrow::Borrow;
use std::fmt::Display;
pattern. The unstable `box` keyword can be used to both create and destructure
a `Box`. An example usage would be:
-```
+```rust
#![feature(box_syntax, box_patterns)]
fn main() {
In many languages with pointers, you'd return a pointer from a function
so as to avoid copying a large data structure. For example:
-```{rust}
+```rust
struct BigStruct {
one: i32,
two: i32,
Rust's standard library provides a library for threads, which allow you to
run Rust code in parallel. Here's a basic example of using `std::thread`:
-```
+```rust
use std::thread;
fn main() {
new thread. It returns a handle to the thread, that can be used to
wait for the child thread to finish and extract its result:
-```
+```rust
use std::thread;
fn main() {
We can use `Arc<T>` to fix this. Here's the working version:
-```
+```rust
use std::sync::{Arc, Mutex};
use std::thread;
Here's a version of our code that uses channels for synchronization, rather
than waiting for a specific time:
-```
+```rust
use std::sync::{Arc, Mutex};
use std::thread;
use std::sync::mpsc;
While this channel is just sending a generic signal, we can send any data that
is `Send` over the channel!
-```
+```rust
use std::thread;
use std::sync::mpsc;
A `panic!` will crash the currently executing thread. You can use Rust's
threads as a simple isolation mechanism:
-```
+```rust
use std::thread;
let result = thread::spawn(move || {
To define each of our modules, we use the `mod` keyword. Let’s make our
`src/lib.rs` look like this:
-```
+```rust
mod english {
mod greetings {
}
Instead of declaring a module like this:
-```{rust,ignore}
+```rust,ignore
mod english {
// contents of our module go here
}
We can instead declare our module like this:
-```{rust,ignore}
+```rust,ignore
mod english;
```
`src/lib.rs` is our crate root, and looks like this:
-```{rust,ignore}
+```rust,ignore
mod english;
mod japanese;
```
chosen the second. Both `src/english/mod.rs` and `src/japanese/mod.rs` look
like this:
-```{rust,ignore}
+```rust,ignore
mod greetings;
mod farewells;
```
keyword. Let’s focus on the `english` module first, so let’s reduce our `src/main.rs`
to just this:
-```{rust,ignore}
+```rust,ignore
extern crate phrases;
fn main() {
In our `src/lib.rs`, let’s add `pub` to the `english` module declaration:
-```{rust,ignore}
+```rust,ignore
pub mod english;
mod japanese;
```
And in our `src/english/mod.rs`, let’s make both `pub`:
-```{rust,ignore}
+```rust,ignore
pub mod greetings;
pub mod farewells;
```
In our `src/english/greetings.rs`, let’s add `pub` to our `fn` declaration:
-```{rust,ignore}
+```rust,ignore
pub fn hello() -> String {
"Hello!".to_string()
}
And also in `src/english/farewells.rs`:
-```{rust,ignore}
+```rust,ignore
pub fn goodbye() -> String {
"Goodbye.".to_string()
}
Rust has a `use` keyword, which allows us to import names into our local scope.
Let’s change our `src/main.rs` to look like this:
-```{rust,ignore}
+```rust,ignore
extern crate phrases;
use phrases::english::greetings;
considered best practice to import the module, rather than the function directly. In
other words, you _can_ do this:
-```{rust,ignore}
+```rust,ignore
extern crate phrases;
use phrases::english::greetings::hello;
error. For example, if we made the `japanese` functions public, and tried to do
this:
-```{rust,ignore}
+```rust,ignore
extern crate phrases;
use phrases::english::greetings::hello;
If we’re importing multiple names from the same module, we don’t have to type it out
twice. Instead of this:
-```{rust,ignore}
+```rust,ignore
use phrases::english::greetings;
use phrases::english::farewells;
```
We can use this shortcut:
-```{rust,ignore}
+```rust,ignore
use phrases::english::{greetings, farewells};
```
Let’s look at an example. Modify your `src/main.rs` to read like this:
-```{rust,ignore}
+```rust,ignore
extern crate phrases;
use phrases::english::{greetings,farewells};
Then, modify your `src/lib.rs` to make the `japanese` mod public:
-```{rust,ignore}
+```rust,ignore
pub mod english;
pub mod japanese;
```
Next, make the two functions public, first in `src/japanese/greetings.rs`:
-```{rust,ignore}
+```rust,ignore
pub fn hello() -> String {
"こんにちは".to_string()
}
And then in `src/japanese/farewells.rs`:
-```{rust,ignore}
+```rust,ignore
pub fn goodbye() -> String {
"さようなら".to_string()
}
Finally, modify your `src/japanese/mod.rs` to read like this:
-```{rust,ignore}
+```rust,ignore
pub use self::greetings::hello;
pub use self::farewells::goodbye;
[paper]: http://www.usingcsp.com/cspbook.pdf
> In ancient times, a wealthy philanthropist endowed a College to accommodate
-> five eminent philosophers. Each philosopher had a room in which he could
-> engage in his professional activity of thinking; there was also a common
+> five eminent philosophers. Each philosopher had a room in which she could
+> engage in her professional activity of thinking; there was also a common
> dining room, furnished with a circular table, surrounded by five chairs, each
> labelled by the name of the philosopher who was to sit in it. They sat
> anticlockwise around the table. To the left of each philosopher there was
> laid a golden fork, and in the centre stood a large bowl of spaghetti, which
-> was constantly replenished. A philosopher was expected to spend most of his
-> time thinking; but when he felt hungry, he went to the dining room, sat down
-> in his own chair, picked up his own fork on his left, and plunged it into the
+> was constantly replenished. A philosopher was expected to spend most of her
+> time thinking; but when she felt hungry, she went to the dining room, sat down
+> in her own chair, picked up her own fork on her left, and plunged it into the
> spaghetti. But such is the tangled nature of spaghetti that a second fork is
> required to carry it to the mouth. The philosopher therefore had also to pick
-> up the fork on his right. When we was finished he would put down both his
-> forks, get up from his chair, and continue thinking. Of course, a fork can be
-> used by only one philosopher at a time. If the other philosopher wants it, he
+> up the fork on her right. When she was finished she would put down both her
+> forks, get up from her chair, and continue thinking. Of course, a fork can be
+> used by only one philosopher at a time. If the other philosopher wants it, she
> just has to wait until the fork is available again.
This classic problem shows off a few different elements of concurrency. The
Rust keeps track of these comments, and uses them when generating
documentation. This is important when documenting things like enums:
-```
+```rust
/// The `Option` type. See [the module level documentation](../) for more.
enum Option<T> {
/// No value
Anyway, let's cover each part of this comment in detail:
-```
+```rust
/// Constructs a new `Rc<T>`.
# fn foo() {}
```
The first line of a documentation comment should be a short summary of its
functionality. One sentence. Just the basics. High level.
-```
+```rust
///
/// Other details about constructing `Rc<T>`s, maybe describing complicated
/// semantics, maybe additional options, all kinds of stuff.
#### Special sections
-```
+```rust
/// # Examples
# fn foo() {}
```
are three kinds of headers that are commonly used. They aren't special syntax,
just convention, for now.
-```
+```rust
/// # Panics
# fn foo() {}
```
least. If your function has a non-trivial contract like this, that is
detected/enforced by panics, documenting it is very important.
-```
+```rust
/// # Failures
# fn foo() {}
```
slightly less important than `Panics`, because failure is encoded into the type
system, but it's still a good thing to do.
-```
+```rust
/// # Safety
# fn foo() {}
```
If your function is `unsafe`, you should explain which invariants the caller is
responsible for upholding.
-```
+```rust
/// # Examples
///
/// ```
code block annotations, which we'll talk about in a moment, and can have
more than one section:
-```
+```rust
/// # Examples
///
/// Simple `&str` patterns:
To write some Rust code in a comment, use the triple graves:
-```
+```rust
/// ```
/// println!("Hello, world");
/// ```
If you want something that's not Rust code, you can add an annotation:
-```
+```rust
/// ```c
/// printf("Hello, world\n");
/// ```
Let's discuss our sample example documentation:
-```
+```rust
/// ```
/// println!("Hello, world");
/// ```
automatically add a main() wrapper around your code, and in the right place.
For example:
-```
+```rust
/// ```
/// use std::rc::Rc;
///
This will end up testing:
-```
+```rust
fn main() {
use std::rc::Rc;
let five = Rc::new(5);
looks different than the output:
-```
+```rust
/// Some documentation.
# fn foo() {}
```
longer examples in detail, while still preserving the testability of your
documentation. For example, this code:
-```
+```rust
let x = 5;
let y = 6;
println!("{}", x + y);
First, we set `x` to five:
-```
+```rust
let x = 5;
# let y = 6;
# println!("{}", x + y);
Next, we set `y` to six:
-```
+```rust
# let x = 5;
let y = 6;
# println!("{}", x + y);
Finally, we print the sum of `x` and `y`:
-```
+```rust
# let x = 5;
# let y = 6;
println!("{}", x + y);
Here’s an example of documenting a macro:
-```
+```rust
/// Panic with a given message unless an expression evaluates to true.
///
/// # Examples
There are a few more annotations that are useful to help `rustdoc` do the right
thing when testing your code:
-```
+```rust
/// ```ignore
/// fn foo() {
/// ```
with `text` if it's not code, or using `#`s to get a working example that
only shows the part you care about.
-```
+```rust
/// ```should_panic
/// assert!(false);
/// ```
`should_panic` tells `rustdoc` that the code should compile correctly, but
not actually pass as a test.
-```
+```rust
/// ```no_run
/// loop {
/// println!("Hello, world");
Rust has another kind of doc comment, `//!`. This comment doesn't document the next item, but the enclosing item. In other words:
-```
+```rust
mod foo {
//! This is documentation for the `foo` module.
//!
This is where you'll see `//!` used most often: for module documentation. If
you have a module in `foo.rs`, you'll often open its code and see this:
-```
+```rust
//! A module for using `foo`s.
//!
//! The `foo` module contains a lot of useful functionality blah blah blah
When you write documentation in Markdown files, you don't need to prefix
the documentation with comments. For example:
-```
+```rust
/// # Examples
///
/// ```
At a deeper level, documentation comments are sugar for documentation attributes:
-```
+```rust
/// this
# fn foo() {}
are the same, as are these:
-```
+```rust
//! this
#![doc="/// this"]
You can control a few aspects of the HTML that `rustdoc` generates through the
`#![doc]` version of the attribute:
-```
+```rust
#![doc(html_logo_url = "http://www.rust-lang.org/logos/rust-logo-128x128-blk-v2.png",
html_favicon_url = "http://www.rust-lang.org/favicon.ico",
html_root_url = "http://doc.rust-lang.org/")];
is very wrong. Wrong enough that we can't continue with things in the current
state. Another example is using the `unreachable!()` macro:
-```{rust,ignore}
+```rust,ignore
enum Event {
NewRelease,
}
In the case of an error that is unexpected and not recoverable, the `panic!`
macro will induce a panic. This will crash the current thread, and give an error:
-```{rust,ignore}
+```rust,ignore
panic!("boom");
```
If we don't want to handle this error, and would rather just abort the program,
we can use the `unwrap()` method:
-```{rust,ignore}
+```rust,ignore
io::stdin().read_line(&mut buffer).unwrap();
```
There's another way of doing this that's a bit nicer than `unwrap()`:
-```{rust,ignore}
+```rust,ignore
let mut buffer = String::new();
let input = io::stdin().read_line(&mut buffer)
.ok()
length is number of elements currently contained, and the capacity is the total size in elements of
the allocated memory. The length is less than or equal to the capacity.
-```
+```rust
# #![feature(libc)]
# extern crate libc;
# use libc::{c_int, size_t};
`snappy_compress` function as an output parameter. An output parameter is also passed to retrieve
the true length after compression for setting the length.
-```
+```rust
# #![feature(libc)]
# extern crate libc;
# use libc::{size_t, c_int};
Decompression is similar, because snappy stores the uncompressed size as part of the compression
format and `snappy_uncompressed_length` will retrieve the exact buffer size required.
-```
+```rust
# #![feature(libc)]
# extern crate libc;
# use libc::{size_t, c_int};
Unsafe functions, on the other hand, advertise it to the world. An unsafe function is written like
this:
-```
+```rust
unsafe fn kaboom(ptr: *const i32) -> i32 { *ptr }
```
calling foreign functions. Some foreign functions, most notably the Windows API, use other calling
conventions. Rust provides a way to tell the compiler which convention to use:
-```
+```rust
# #![feature(libc)]
extern crate libc;
You may wish to compile Rust code in a way so that it can be called from C. This is
fairly easy, but requires a few things:
-```
+```rust
#[no_mangle]
pub extern fn hello_rust() -> *const u8 {
"Hello, world!\0".as_ptr()
languages where an assignment evaluates to the assigned value (e.g. `5` in the
previous example), in Rust the value of an assignment is an empty tuple `()`:
-```
+```rust
let mut y = 5;
let x = (y = 6); // x has the value `()`, not `6`
Rust has some special syntax for ‘diverging functions’, which are functions that
do not return:
-```
+```rust
fn diverges() -> ! {
panic!("This function never returns!");
}
You can store a generic type in a `struct` as well:
-```
+```rust
struct Point<T> {
x: T,
y: T,
‘[pattern][patterns]’. We’ll use patterns more later. It’s easy enough
to use for now:
-```
+```rust
let foo = 5; // immutable.
let mut bar = 5; // mutable
```
The `assembly template` is the only required parameter and must be a
literal string (i.e. `""`)
-```
+```rust
#![feature(asm)]
#[cfg(any(target_arch = "x86", target_arch = "x86_64"))]
Output operands, input operands, clobbers and options are all optional
but you must add the right number of `:` if you skip them:
-```
+```rust
# #![feature(asm)]
# #[cfg(any(target_arch = "x86", target_arch = "x86_64"))]
# fn main() { unsafe {
Whitespace also doesn't matter:
-```
+```rust
# #![feature(asm)]
# #[cfg(any(target_arch = "x86", target_arch = "x86_64"))]
# fn main() { unsafe {
"constraints1"(expr1), "constraints2"(expr2), ..."`. Output operand
expressions must be mutable lvalues, or not yet assigned:
-```
+```rust
# #![feature(asm)]
# #[cfg(any(target_arch = "x86", target_arch = "x86_64"))]
fn add(a: i32, b: i32) -> i32 {
operand. This is useful for very low level programming, where
which register you use is important:
-```
+```rust
# #![feature(asm)]
# #[cfg(any(target_arch = "x86", target_arch = "x86_64"))]
# unsafe fn read_byte_in(port: u16) -> u8 {
compiler not to assume any values loaded into those registers will
stay valid.
-```
+```rust
# #![feature(asm)]
# #[cfg(any(target_arch = "x86", target_arch = "x86_64"))]
# fn main() { unsafe {
the compiler to insert its usual stack alignment code
3. *intel* - use intel syntax instead of the default AT&T.
-```
+```rust
# #![feature(asm)]
# #[cfg(any(target_arch = "x86", target_arch = "x86_64"))]
# fn main() {
perform efficient pointer arithmetic, one would import those functions
via a declaration like
-```
+```rust
# #![feature(intrinsics)]
# fn main() {}
The most common consumer is `collect()`. This code doesn't quite compile,
but it shows the intention:
-```{rust,ignore}
+```rust,ignore
let one_to_one_hundred = (1..101).collect();
```
*Iterator adapters* take an iterator and modify it somehow, producing
a new iterator. The simplest one is called `map`:
-```{rust,ignore}
+```rust,ignore
(1..100).map(|x| x + 1);
```
Laziness strikes again! That closure will never execute. This example
doesn't print any numbers:
-```{rust,ignore}
+```rust,ignore
(1..100).map(|x| println!("{}", x));
```
and one for deallocation. A freestanding program that uses the `Box`
sugar for dynamic allocations via `malloc` and `free`:
-```
+```rust
#![feature(lang_items, box_syntax, start, no_std, libc)]
#![no_std]
## Lifetime Elision
Rust supports powerful local type inference in function bodies, but it’s
-forbidden in item signatures to allow reasoning about the types just based in
+forbidden in item signatures to allow reasoning about the types based on
the item signature alone. However, for ergonomic reasons a very restricted
secondary inference algorithm called “lifetime elision” applies in function
signatures. It infers only based on the signature components themselves and not
## assert! and assert_eq!
-These two macros are used in tests. `assert!` takes a boolean, and `assert_eq!`
-takes two values and compares them. Truth passes, success `panic!`s. Like
-this:
+These two macros are used in tests. `assert!` takes a boolean. `assert_eq!`
+takes two values and checks them for equality. `true` passes, `false` `panic!`s.
+Like this:
```rust,no_run
// A-ok!
assert!(5 < 3);
assert_eq!(5, 3);
```
+
## try!
`try!` is used for error handling. It takes something that can return a
original example, `foo.bar().baz()`? This is called ‘method chaining’, and we
can do it by returning `self`.
-```
+```rust
struct Circle {
x: f64,
y: f64,
Check the return type:
-```
+```rust
# struct Circle;
# impl Circle {
fn grow(&self) -> Circle {
have method overloading, named arguments, or variable arguments. We employ
the builder pattern instead. It looks like this:
-```
+```rust
struct Circle {
x: f64,
y: f64,
However, by using `Cell<T>`, you can emulate field-level mutability:
-```
+```rust
use std::cell::Cell;
struct Point {
The function marked `#[start]` is passed the command line parameters
in the same format as C:
-```
+```rust
#![feature(lang_items, start, no_std, libc)]
#![no_std]
You can disambiguate a single-element tuple from a value in parentheses with a
comma:
-```
+```rust
(0,); // single-element tuple
(0); // zero in parentheses
```
Functions also have a type! They look like this:
-```
+```rust
fn foo(x: i32) -> i32 { x }
let x: fn(i32) -> i32 = foo;
`String`s will coerce into `&str` with an `&`:
-```
+```rust
fn takes_slice(slice: &str) {
println!("Got: {}", slice);
}
make sure that the failure message contains the provided text. A safer version
of the example above would be:
-```
+```rust
#[test]
#[should_panic(expected = "assertion failed")]
fn it_works() {
That's all there is to the basics! Let's write one 'real' test:
-```{rust,ignore}
+```rust,ignore
pub fn add_two(a: i32) -> i32 {
a + 2
}
missing the `tests` module. The idiomatic way of writing our example
looks like this:
-```{rust,ignore}
+```rust,ignore
pub fn add_two(a: i32) -> i32 {
a + 2
}
a large module, and so this is a common use of the `glob` feature. Let's change
our `src/lib.rs` to make use of it:
-```{rust,ignore}
+```rust,ignore
pub fn add_two(a: i32) -> i32 {
a + 2
To write an integration test, let's make a `tests` directory, and
put a `tests/lib.rs` file inside, with this as its contents:
-```{rust,ignore}
+```rust,ignore
extern crate adder;
#[test]
running examples in your documentation. Here's a fleshed-out `src/lib.rs`
with examples:
-```{rust,ignore}
+```rust,ignore
//! The `adder` crate provides functions that add numbers to other numbers.
//!
//! # Examples
```rust,ignore
let mut f = std::fs::File::open("foo.txt").ok().expect("Couldn’t open foo.txt");
-let result = f.write("whatever".as_bytes());
+let buf = b"whatever"; // byte string literal. buf: &[u8; 8]
+let result = f.write(buf);
# result.unwrap(); // ignore the error
```
```text
error: type `std::fs::File` does not implement any method in scope named `write`
-
-let result = f.write(b"whatever");
- ^~~~~~~~~~~~~~~~~~
+let result = f.write(buf);
+ ^~~~~~~~~~
```
We need to `use` the `Write` trait first:
use std::io::Write;
let mut f = std::fs::File::open("foo.txt").ok().expect("Couldn’t open foo.txt");
-let result = f.write("whatever".as_bytes());
+let buf = b"whatever";
+let result = f.write(buf);
# result.unwrap(); // ignore the error
```
bounds isn’t too bad, but as the number increases, the syntax gets increasingly
awkward:
-```
+```rust
use std::fmt::Debug;
fn foo<T: Clone, K: Clone + Debug>(x: T, y: K) {
Rust has a solution, and it’s called a ‘`where` clause’:
-```
+```rust
use std::fmt::Debug;
fn foo<T: Clone, K: Clone + Debug>(x: T, y: K) {
and then add `where` after the parameter list. For longer lists, whitespace can
be added:
-```
+```rust
use std::fmt::Debug;
fn bar<T, K>(x: T, y: K)
`where` is also more powerful than the simpler syntax. For example:
-```
+```rust
trait ConvertTo<Output> {
fn convert(&self) -> Output;
}
There’s an alternate form of `vec!` for repeating an initial value:
-```
+```rust
let v = vec![0; 10]; // ten zeroes
```
Rust also has a `while` loop. It looks like this:
-```{rust}
+```rust
let mut x = 5; // mut x: i32
let mut done = false; // mut done: bool
//! * `^` - the argument is center-aligned in `width` columns
//! * `>` - the argument is right-aligned in `width` columns
//!
+//! Note that alignment may not be implemented by some types. A good way
+//! to ensure padding is applied is to format your input, then use this
+//! resulting string to pad your output.
+//!
//! ## Sign/#/0
//!
//! These can all be interpreted as flags for a particular formatter.
///
/// # Examples
///
+ /// ```
/// let s = "HELLO";
/// assert_eq!(s.to_lowercase(), "hello");
+ /// ```
#[unstable(feature = "collections")]
pub fn to_lowercase(&self) -> String {
let mut s = String::with_capacity(self.len());
///
/// # Examples
///
+ /// ```
/// let s = "hello";
/// assert_eq!(s.to_uppercase(), "HELLO");
+ /// ```
#[unstable(feature = "collections")]
pub fn to_uppercase(&self) -> String {
let mut s = String::with_capacity(self.len());
}
/// Returns `a` < `b` lexicographically (Using partial order, `PartialOrd`)
- pub fn lt<R: Iterator, L: Iterator>(mut a: L, mut b: R) -> bool where
+ pub fn lt<L: Iterator, R: Iterator>(mut a: L, mut b: R) -> bool where
L::Item: PartialOrd<R::Item>,
{
loop {
///
/// Leading and trailing whitespace represent an error.
///
- /// # Arguments
- ///
- /// * src - A string slice
- /// * radix - The base to use. Must lie in the range [2 .. 36]
- ///
- /// # Return value
+ /// # Examples
///
- /// `Err(ParseIntError)` if the string did not represent a valid number.
- /// Otherwise, `Ok(n)` where `n` is the integer represented by `src`.
+ /// ```
+ /// assert_eq!(u32::from_str_radix("A", 16), Some(10));
+ /// ```
#[stable(feature = "rust1", since = "1.0.0")]
#[allow(deprecated)]
pub fn from_str_radix(src: &str, radix: u32) -> Result<$T, ParseIntError> {
register_long_diagnostics! {
+E0023: r##"
+A pattern used to match against an enum variant must provide a sub-pattern for
+each field of the enum variant. This error indicates that a pattern attempted to
+extract an incorrect number of fields from a variant.
+
+```
+enum Fruit {
+ Apple(String, String)
+ Pear(u32)
+}
+```
+
+Here the `Apple` variant has two fields, and should be matched against like so:
+
+```
+// Correct.
+match x {
+ Apple(a, b) => ...
+}
+```
+
+Matching with the wrong number of fields has no sensible interpretation:
+
+```
+// Incorrect.
+match x {
+ Apple(a) => ...,
+ Apple(a, b, c) => ...
+}
+```
+
+Check how many fields the enum was declared with and ensure that your pattern
+uses the same number.
+"##,
+
+E0024: r##"
+This error indicates that a pattern attempted to extract the fields of an enum
+variant with no fields. Here's a tiny example of this error:
+
+```
+// This enum has two variants.
+enum Number {
+ // This variant has no fields.
+ Zero,
+ // This variant has one field.
+ One(u32)
+}
+
+// Assuming x is a Number we can pattern match on its contents.
+match x {
+ Zero(inside) => ...,
+ One(inside) => ...
+}
+```
+
+The pattern match `Zero(inside)` is incorrect because the `Zero` variant
+contains no fields, yet the `inside` name attempts to bind the first field of
+the enum.
+"##,
+
+E0025: r##"
+Each field of a struct can only be bound once in a pattern. Each occurrence of a
+field name binds the value of that field, so to fix this error you will have to
+remove or alter the duplicate uses of the field name. Perhaps you misspelt
+another field name?
+"##,
+
+E0026: r##"
+This error indicates that a struct pattern attempted to extract a non-existant
+field from a struct. Struct fields are identified by the name used before the
+colon `:` so struct patterns should resemble the declaration of the struct type
+being matched.
+
+```
+// Correct matching.
+struct Thing {
+ x: u32,
+ y: u32
+}
+
+let thing = Thing { x: 1, y: 2 };
+match thing {
+ Thing { x: xfield, y: yfield } => ...
+}
+```
+
+If you are using shorthand field patterns but want to refer to the struct field
+by a different name, you should rename it explicitly.
+
+```
+// Change this:
+match thing {
+ Thing { x, z } => ...
+}
+
+// To this:
+match thing {
+ Thing { x, y: z } => ...
+}
+```
+"##,
+
+E0027: r##"
+This error indicates that a pattern for a struct fails to specify a sub-pattern
+for every one of the struct's fields. Ensure that each field from the struct's
+definition is mentioned in the pattern, or use `..` to ignore unwanted fields.
+
+For example:
+
+```
+struct Dog {
+ name: String,
+ age: u32
+}
+
+let d = Dog { name: "Rusty".to_string(), age: 8 };
+
+// This is incorrect.
+match d {
+ Dog { age: x } => ...
+}
+
+// This is correct (explicit).
+match d {
+ Dog { name: n, age: x } => ...
+}
+
+// This is also correct (ignore unused fields).
+match d {
+ Dog { age: x, .. } => ...
+}
+```
+"##,
+
+E0033: r##"
+This error indicates that a pointer to a trait type cannot be implicitly
+dereferenced by a pattern. Every trait defines a type, but because the
+size of trait implementors isn't fixed, this type has no compile-time size.
+Therefore, all accesses to trait types must be through pointers. If you
+encounter this error you should try to avoid dereferencing the pointer.
+
+```
+let trait_obj: &SomeTrait = ...;
+
+// This tries to implicitly dereference to create an unsized local variable.
+let &invalid = trait_obj;
+
+// You can call methods without binding to the value being pointed at.
+trait_obj.method_one();
+trait_obj.method_two();
+```
+
+You can read more about trait objects in the Trait Object section of the
+Reference:
+
+http://doc.rust-lang.org/reference.html#trait-objects
+"##,
+
E0046: r##"
When trying to make some type implement a trait `Foo`, you must, at minimum,
provide implementations for all of `Foo`'s required methods (meaning the
}
register_diagnostics! {
- E0023,
- E0024,
- E0025,
- E0026,
- E0027,
E0029,
E0030,
E0031,
- E0033,
E0034, // multiple applicable methods in scope
E0035, // does not take type parameters
E0036, // incorrect number of type parameters given for this method
.content .impl-items .docblock, .content .impl-items .stability {
margin-left: 40px;
}
-.content .impl-items .method, .content .impl-items .type {
+.content .impl-items .method, .content .impl-items > .type {
margin-left: 20px;
}
/// Utility methods for paths.
#[unstable(feature = "path_ext",
- reason = "the precise set of methods exposed on this trait may \
- change and some methods may be removed")]
+ reason = "The precise set of methods exposed on this trait may \
+ change and some methods may be removed. For stable code, \
+ see the std::fs::metadata function.")]
pub trait PathExt {
/// Gets information on the file, directory, etc at this path.
///
unsafe { self.handle.kill() }
}
+ /// Returns the OS-assigned process identifier associated with this child.
+ #[unstable(feature = "process_id", reason = "api recently added")]
+ pub fn id(&self) -> u32 {
+ self.handle.id()
+ }
+
/// Waits for the child to exit completely, returning the status that it
/// exited with. This function will continue to have the same return value
/// after it has been called at least once.
fail(&mut output)
}
+ pub fn id(&self) -> u32 {
+ self.pid as u32
+ }
+
pub fn wait(&self) -> io::Result<ExitStatus> {
let mut status = 0 as c_int;
try!(cvt_r(|| unsafe { c::waitpid(self.pid, &mut status, 0) }));
dwMilliseconds: libc::DWORD) -> libc::DWORD;
pub fn SwitchToThread() -> libc::BOOL;
pub fn Sleep(dwMilliseconds: libc::DWORD);
+ pub fn GetProcessId(handle: libc::HANDLE) -> libc::DWORD;
}
#[link(name = "userenv")]
Ok(())
}
+ pub fn id(&self) -> u32 {
+ unsafe {
+ c::GetProcessId(self.handle.raw()) as u32
+ }
+ }
+
pub fn wait(&self) -> io::Result<ExitStatus> {
use libc::{STILL_ACTIVE, INFINITE, WAIT_OBJECT_0};
use libc::{GetExitCodeProcess, WaitForSingleObject};
}
}
-fn write_toc(book: &Book, path_to_root: &Path, out: &mut Write) -> io::Result<()> {
+fn write_toc(book: &Book, current_page: &BookItem, out: &mut Write) -> io::Result<()> {
fn walk_items(items: &[BookItem],
section: &str,
- path_to_root: &Path,
+ current_page: &BookItem,
out: &mut Write) -> io::Result<()> {
for (i, item) in items.iter().enumerate() {
- try!(walk_item(item, &format!("{}{}.", section, i + 1)[..], path_to_root, out));
+ try!(walk_item(item, &format!("{}{}.", section, i + 1)[..], current_page, out));
}
Ok(())
}
fn walk_item(item: &BookItem,
section: &str,
- path_to_root: &Path,
+ current_page: &BookItem,
out: &mut Write) -> io::Result<()> {
- try!(writeln!(out, "<li><a href='{}'><b>{}</b> {}</a>",
- path_to_root.join(&item.path.with_extension("html")).display(),
+ let class_string = if item.path == current_page.path {
+ "class='active'"
+ } else {
+ ""
+ };
+
+ try!(writeln!(out, "<li><a {} href='{}'><b>{}</b> {}</a>",
+ class_string,
+ item.path_to_root.join(&item.path.with_extension("html")).display(),
section,
item.title));
if !item.children.is_empty() {
try!(writeln!(out, "<ul class='section'>"));
- let _ = walk_items(&item.children[..], section, path_to_root, out);
+ let _ = walk_items(&item.children[..], section, current_page, out);
try!(writeln!(out, "</ul>"));
}
try!(writeln!(out, "</li>"));
try!(writeln!(out, "<div id='toc' class='mobile-hidden'>"));
try!(writeln!(out, "<ul class='chapter'>"));
- try!(walk_items(&book.chapters[..], "", path_to_root, out));
+ try!(walk_items(&book.chapters[..], "", ¤t_page, out));
try!(writeln!(out, "</ul>"));
try!(writeln!(out, "</div>"));
<span class="bar"></span>
</button>
</div>"#));
- let _ = write_toc(book, &item.path_to_root, &mut toc);
+ let _ = write_toc(book, &item, &mut toc);
try!(writeln!(&mut toc, "<div id='page-wrapper'>"));
try!(writeln!(&mut toc, "<div id='page'>"));
}
color: #000000;
}
+.chapter li a.active {
+ text-decoration: underline;
+ font-weight: bold;
+}
+
#toggle-nav {
height: 20px;
width: 30px;