From 0f5ba5459b8cf75be84ab9951de379a3f9d1f9d5 Mon Sep 17 00:00:00 2001 From: Steve Klabnik Date: Tue, 17 Nov 2015 11:12:57 -0500 Subject: [PATCH 1/6] Mention libc from crates.io in TRPL: FFI Fixes #29762 --- src/doc/trpl/ffi.md | 17 +++++++++++++++++ 1 file changed, 17 insertions(+) diff --git a/src/doc/trpl/ffi.md b/src/doc/trpl/ffi.md index 7a58a327b9f..d949bf33b6e 100644 --- a/src/doc/trpl/ffi.md +++ b/src/doc/trpl/ffi.md @@ -8,6 +8,23 @@ foreign code. Rust is currently unable to call directly into a C++ library, but snappy includes a C interface (documented in [`snappy-c.h`](https://github.com/google/snappy/blob/master/snappy-c.h)). +## A note about libc + +Many of these examples use [the `libc` crate][libc], which provides various +type definitions for C types, among other things. If you’re trying these +examples yourself, you’ll need to add `libc` to your `Cargo.toml`: + +```toml +[dependencies] +libc = "0.2.0" +``` + +[libc]: https://crates.io/crates/libc + +and add `extern crate libc;` to your crate root. + +## Calling foreign functions + The following is a minimal example of calling a foreign function which will compile if snappy is installed: From dcf7e4da692661a12113144bebda99f84d76db47 Mon Sep 17 00:00:00 2001 From: Steve Klabnik Date: Tue, 17 Nov 2015 11:42:17 -0500 Subject: [PATCH 2/6] Clarify comment about structs and lifetimes FIxes #29742 --- src/doc/trpl/lifetimes.md | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/src/doc/trpl/lifetimes.md b/src/doc/trpl/lifetimes.md index 13265ab1eba..68bbd0c9899 100644 --- a/src/doc/trpl/lifetimes.md +++ b/src/doc/trpl/lifetimes.md @@ -116,7 +116,8 @@ reference to an `i32` with the lifetime `'a`’. # In `struct`s -You’ll also need explicit lifetimes when working with [`struct`][structs]s: +You’ll also need explicit lifetimes when working with [`struct`][structs]s that +contain references: ```rust struct Foo<'a> { From 9ca257a5b612faa1fd0abd83608bab63393dcf5a Mon Sep 17 00:00:00 2001 From: Steve Klabnik Date: Tue, 17 Nov 2015 11:54:20 -0500 Subject: [PATCH 3/6] Fix up escapes in the reference Fixes #29470 --- src/doc/reference.md | 15 +++++++++++---- 1 file changed, 11 insertions(+), 4 deletions(-) diff --git a/src/doc/reference.md b/src/doc/reference.md index de9352a4275..e8ad1afa9af 100644 --- a/src/doc/reference.md +++ b/src/doc/reference.md @@ -147,11 +147,11 @@ a form of constant expression, so is evaluated (primarily) at compile time. | | Example | `#` sets | Characters | Escapes | |----------------------------------------------|-----------------|------------|-------------|---------------------| -| [Character](#character-literals) | `'H'` | `N/A` | All Unicode | `\'` & [Byte](#byte-escapes) & [Unicode](#unicode-escapes) | -| [String](#string-literals) | `"hello"` | `N/A` | All Unicode | `\"` & [Byte](#byte-escapes) & [Unicode](#unicode-escapes) | +| [Character](#character-literals) | `'H'` | `N/A` | All Unicode | [Quote](#quote-escapes) & [Byte](#byte-escapes) & [Unicode](#unicode-escapes) | +| [String](#string-literals) | `"hello"` | `N/A` | All Unicode | [Quote](#quote-escapes) & [Byte](#byte-escapes) & [Unicode](#unicode-escapes) | | [Raw](#raw-string-literals) | `r#"hello"#` | `0...` | All Unicode | `N/A` | -| [Byte](#byte-literals) | `b'H'` | `N/A` | All ASCII | `\'` & [Byte](#byte-escapes) | -| [Byte string](#byte-string-literals) | `b"hello"` | `N/A` | All ASCII | `\"` & [Byte](#byte-escapes) | +| [Byte](#byte-literals) | `b'H'` | `N/A` | All ASCII | [Quote](#quote-escapes) & [Byte](#byte-escapes) | +| [Byte string](#byte-string-literals) | `b"hello"` | `N/A` | All ASCII | [Quote](#quote-escapes) & [Byte](#byte-escapes) | | [Raw byte string](#raw-byte-string-literals) | `br#"hello"#` | `0...` | All ASCII | `N/A` | ##### Byte escapes @@ -163,12 +163,19 @@ a form of constant expression, so is evaluated (primarily) at compile time. | `\r` | Carriage return | | `\t` | Tab | | `\\` | Backslash | +| `\0` | Null | ##### Unicode escapes | | Name | |---|------| | `\u{7FFF}` | 24-bit Unicode character code (up to 6 digits) | +##### Quote escapes +| | Name | +|---|------| +| `\'` | Single quote | +| `\"` | Double quote | + ##### Numbers | [Number literals](#number-literals)`*` | Example | Exponentiation | Suffixes | From cf384c21eae3f9bd7e8d1f76ced8ad7199cd02f4 Mon Sep 17 00:00:00 2001 From: Steve Klabnik Date: Tue, 17 Nov 2015 11:31:13 -0500 Subject: [PATCH 4/6] Clear up the reference around let First, re-word the section on if let/while let to be more clear. Second, actually call them let statements in the statement section Fixes #29801 --- src/doc/reference.md | 23 ++++++++++++----------- 1 file changed, 12 insertions(+), 11 deletions(-) diff --git a/src/doc/reference.md b/src/doc/reference.md index de9352a4275..b057b846be7 100644 --- a/src/doc/reference.md +++ b/src/doc/reference.md @@ -2415,9 +2415,9 @@ in meaning to declaring the item outside the statement block. > **Note**: there is no implicit capture of the function's dynamic environment when > declaring a function-local item. -#### Variable declarations +#### `let` statements -A _variable declaration_ introduces a new set of variable, given by a pattern. The +A _`let` statement_ introduces a new set of variables, given by a pattern. The pattern may be followed by a type annotation, and/or an initializer expression. When no type annotation is given, the compiler will infer the type, or signal an error if insufficient type information is available for definite inference. @@ -3190,10 +3190,11 @@ let message = match maybe_digit { ### `if let` expressions -An `if let` expression is semantically identical to an `if` expression but in place -of a condition expression it expects a refutable let statement. If the value of the -expression on the right hand side of the let statement matches the pattern, the corresponding -block will execute, otherwise flow proceeds to the first `else` block that follows. +An `if let` expression is semantically identical to an `if` expression but in +place of a condition expression it expects a `let` statement with a refutable +pattern. If the value of the expression on the right hand side of the `let` +statement matches the pattern, the corresponding block will execute, otherwise +flow proceeds to the first `else` block that follows. ``` let dish = ("Ham", "Eggs"); @@ -3211,11 +3212,11 @@ if let ("Ham", b) = dish { ### `while let` loops -A `while let` loop is semantically identical to a `while` loop but in place of a -condition expression it expects a refutable let statement. If the value of the -expression on the right hand side of the let statement matches the pattern, the -loop body block executes and control returns to the pattern matching statement. -Otherwise, the while expression completes. +A `while let` loop is semantically identical to a `while` loop but in place of +a condition expression it expects `let` statement with a refutable pattern. If +the value of the expression on the right hand side of the `let` statement +matches the pattern, the loop body block executes and control returns to the +pattern matching statement. Otherwise, the while expression completes. ### `return` expressions From 60c84eed42c03ac6cfed92c256ce2b3be3199140 Mon Sep 17 00:00:00 2001 From: Steve Klabnik Date: Thu, 5 Nov 2015 14:33:30 +0100 Subject: [PATCH 5/6] Remove claims of dependency-free libcore libcore does have a few deps, like noted in https://github.com/rust-lang/rust/issues/29390 Fixes #29502 --- src/libcore/lib.rs | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/src/libcore/lib.rs b/src/libcore/lib.rs index df7b7c437c3..263d01a5d26 100644 --- a/src/libcore/lib.rs +++ b/src/libcore/lib.rs @@ -10,12 +10,15 @@ //! # The Rust Core Library //! -//! The Rust Core Library is the dependency-free foundation of [The +//! The Rust Core Library is the dependency-free[^free] foundation of [The //! Rust Standard Library](../std/index.html). It is the portable glue //! between the language and its libraries, defining the intrinsic and //! primitive building blocks of all Rust code. It links to no //! upstream libraries, no system libraries, and no libc. //! +//! [^free]: Strictly speaking, there are some symbols which are needed but +//! they aren't always neccesary. +//! //! The core library is *minimal*: it isn't even aware of heap allocation, //! nor does it provide concurrency or I/O. These things require //! platform integration, and this library is platform-agnostic. From 9d663a3e4a85be4c45194cd1c987dd77dee45ab7 Mon Sep 17 00:00:00 2001 From: Steve Klabnik Date: Tue, 17 Nov 2015 12:42:09 -0500 Subject: [PATCH 6/6] More docs for FromIterator And modifying IntoIterator for consisntency with it. Part of #29360 --- src/libcore/iter.rs | 148 +++++++++++++++++++++++++++++++++++++++----- 1 file changed, 132 insertions(+), 16 deletions(-) diff --git a/src/libcore/iter.rs b/src/libcore/iter.rs index 8558927e4ac..020f7e37a4a 100644 --- a/src/libcore/iter.rs +++ b/src/libcore/iter.rs @@ -2375,32 +2375,118 @@ impl<'a, I: Iterator + ?Sized> Iterator for &'a mut I { } /// Conversion from an `Iterator`. +/// +/// By implementing `FromIterator` for a type, you define how it will be +/// created from an iterator. This is common for types which describe a +/// collection of some kind. +/// +/// `FromIterator`'s [`from_iter()`] is rarely called explicitly, and is instead +/// used through [`Iterator`]'s [`collect()`] method. See [`collect()`]'s +/// documentation for more examples. +/// +/// [`from_iter()`]: #tymethod.from_iter +/// [`Iterator`]: trait.Iterator.html +/// [`collect()`]: trait.Iterator.html#method.collect +/// +/// See also: [`IntoIterator`]. +/// +/// [`IntoIterator`]: trait.IntoIterator.html +/// +/// # Examples +/// +/// Basic usage: +/// +/// ``` +/// use std::iter::FromIterator; +/// +/// let five_fives = std::iter::repeat(5).take(5); +/// +/// let v = Vec::from_iter(five_fives); +/// +/// assert_eq!(v, vec![5, 5, 5, 5, 5]); +/// ``` +/// +/// Using [`collect()`] to implicitly use `FromIterator`: +/// +/// ``` +/// let five_fives = std::iter::repeat(5).take(5); +/// +/// let v: Vec = five_fives.collect(); +/// +/// assert_eq!(v, vec![5, 5, 5, 5, 5]); +/// ``` +/// +/// Implementing `FromIterator` for your type: +/// +/// ``` +/// use std::iter::FromIterator; +/// +/// // A sample collection, that's just a wrapper over Vec +/// #[derive(Debug)] +/// struct MyCollection(Vec); +/// +/// // Let's give it some methods so we can create one and add things +/// // to it. +/// impl MyCollection { +/// fn new() -> MyCollection { +/// MyCollection(Vec::new()) +/// } +/// +/// fn add(&mut self, elem: i32) { +/// self.0.push(elem); +/// } +/// } +/// +/// // and we'll implement FromIterator +/// impl FromIterator for MyCollection { +/// fn from_iter>(iterator: I) -> Self { +/// let mut c = MyCollection::new(); +/// +/// for i in iterator { +/// c.add(i); +/// } +/// +/// c +/// } +/// } +/// +/// // Now we can make a new iterator... +/// let iter = (0..5).into_iter(); +/// +/// // ... and make a MyCollection out of it +/// let c = MyCollection::from_iter(iter); +/// +/// assert_eq!(c.0, vec![0, 1, 2, 3, 4]); +/// +/// // collect works too! +/// +/// let iter = (0..5).into_iter(); +/// let c: MyCollection = iter.collect(); +/// +/// assert_eq!(c.0, vec![0, 1, 2, 3, 4]); +/// ``` #[stable(feature = "rust1", since = "1.0.0")] #[rustc_on_unimplemented="a collection of type `{Self}` cannot be \ built from an iterator over elements of type `{A}`"] pub trait FromIterator: Sized { - /// Builds a container with elements from something iterable. + /// Creates a value from an iterator. + /// + /// See the [module-level documentation] for more. + /// + /// [module-level documentation]: trait.FromIterator.html /// /// # Examples /// + /// Basic usage: + /// /// ``` - /// use std::collections::HashSet; /// use std::iter::FromIterator; /// - /// let colors_vec = vec!["red", "red", "yellow", "blue"]; - /// let colors_set = HashSet::<&str>::from_iter(colors_vec); - /// assert_eq!(colors_set.len(), 3); - /// ``` + /// let five_fives = std::iter::repeat(5).take(5); /// - /// `FromIterator` is more commonly used implicitly via the - /// `Iterator::collect` method: + /// let v = Vec::from_iter(five_fives); /// - /// ``` - /// use std::collections::HashSet; - /// - /// let colors_vec = vec!["red", "red", "yellow", "blue"]; - /// let colors_set = colors_vec.into_iter().collect::>(); - /// assert_eq!(colors_set.len(), 3); + /// assert_eq!(v, vec![5, 5, 5, 5, 5]); /// ``` #[stable(feature = "rust1", since = "1.0.0")] fn from_iter>(iterator: T) -> Self; @@ -2415,9 +2501,13 @@ pub trait FromIterator: Sized { /// One benefit of implementing `IntoIterator` is that your type will [work /// with Rust's `for` loop syntax](index.html#for-loops-and-intoiterator). /// +/// See also: [`FromIterator`]. +/// +/// [`FromIterator`]: trait.FromIterator.html +/// /// # Examples /// -/// Vectors implement `IntoIterator`: +/// Basic usage: /// /// ``` /// let v = vec![1, 2, 3]; @@ -2489,7 +2579,33 @@ pub trait IntoIterator { #[stable(feature = "rust1", since = "1.0.0")] type IntoIter: Iterator; - /// Consumes `Self` and returns an iterator over it. + /// Creates an iterator from a value. + /// + /// See the [module-level documentation] for more. + /// + /// [module-level documentation]: trait.IntoIterator.html + /// + /// # Examples + /// + /// Basic usage: + /// + /// ``` + /// let v = vec![1, 2, 3]; + /// + /// let mut iter = v.into_iter(); + /// + /// let n = iter.next(); + /// assert_eq!(Some(1), n); + /// + /// let n = iter.next(); + /// assert_eq!(Some(2), n); + /// + /// let n = iter.next(); + /// assert_eq!(Some(3), n); + /// + /// let n = iter.next(); + /// assert_eq!(None, n); + /// ``` #[stable(feature = "rust1", since = "1.0.0")] fn into_iter(self) -> Self::IntoIter; }