mirror of
https://github.com/gnu4cn/rust-lang-zh_CN.git
synced 2026-08-19 12:43:28 +08:00
Updated src/common_collections/string.md'.
This commit is contained in:
@@ -1,8 +1,6 @@
|
||||
[package]
|
||||
name = "string_demo"
|
||||
version = "0.1.0"
|
||||
edition = "2021"
|
||||
|
||||
# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html
|
||||
edition = "2024"
|
||||
|
||||
[dependencies]
|
||||
|
||||
@@ -1,11 +1,10 @@
|
||||
fn main() {
|
||||
let s = "नमस्ते";
|
||||
let data = "初始内容";
|
||||
|
||||
for c in s.chars() {
|
||||
println! ("{}", c);
|
||||
}
|
||||
let s = data.to_string();
|
||||
|
||||
for b in s.bytes() {
|
||||
println! ("{}", b);
|
||||
}
|
||||
// 该方法直接在字面值之上也工作
|
||||
let s = "初始内容".to_string();
|
||||
|
||||
println! ("{s}");
|
||||
}
|
||||
|
||||
@@ -1,69 +1,69 @@
|
||||
# 以字符串存储 UTF-8 编码的文本
|
||||
|
||||
在第 4 章中,我们曾讨论过字符串,现在我们将对其进行更深入的研究。新的 Rust 公民通常卡在字符串上,原因有三:
|
||||
我们在第 4 章中讨论过字符串,而现在我们将更深入研究他们。新手 Rustacean 们通常会因为以下三个原因的结合,而在字符串上陷入困境:
|
||||
|
||||
- Rust 有暴露可能错误的倾向;
|
||||
- 字符串是种比许多程序员认为的更复杂的数据结构;
|
||||
- Rust 暴露可能错误的倾向;
|
||||
- 字符串属于一种比许多程序员所认为的更复杂的数据结构;
|
||||
- 以及 UTF-8。
|
||||
|
||||
当咱们从其他编程语言转至 Rust 时,这些因素就会以看起来很难的方式,纠缠在一起。
|
||||
当咱们来从其他编程语言时,这些因素以一种看似困难的方式结合在一起。
|
||||
|
||||
|
||||
我们之所以会在集合语境下讨论字符串,是因为字符串是作为字节集合,加上一些在这些字节被解释为文本时,提供有用功能的方法实现的。在本节中,我们将讨论那些 `String` 上的、每种集合类型都有的操作,比如创建、更新及读取等。我们还将讨论 `String` 与其他集合的不同之处,即由于人与计算机在解析 `String` 数据时的差异,而对 `String` 的索引会变得如何复杂。
|
||||
我们之所以会在集合的上下文中讨论字符串,是因为字符串是作为字节的集合实现的,加上一些在这些字节被解释为文本时提供有用功能的方法。在这一小节中,我们将讨论 `String` 上的、每种集合类型都有的操作,比如创建、更新及读取等。我们还将讨论 `String` 与其他集合的不同之处,即由于人与计算机在解析 `String` 数据方式上的差异,而怎样导致对 `String` 的索引会变得复杂。
|
||||
|
||||
|
||||
## 何为字符串?
|
||||
## 定义字符串
|
||||
|
||||
我们将首先定义 *字符串* 这一术语的含义。Rust 在核心语言中只有一种字符串类型,即通常以其借用形式 `&str` 看到的字符串切片 `str`。在第 4 章中,我们讨论过 [字符串切片](../ownership/the_slice_type.md#字符串切片),他们属于对存储在别处的一些 UTF-8 编码字符串数据的引用。例如,字符串的字面值存储在程序的二进制文件中,而因此属于字符串切片。
|
||||
|
||||
所谓 `String` 类型,是由 Rust 的标准库提供而非编码到核心语言中,是一种可增长、可变、被拥有(所有权)、UTF-8 编码的字符串类型。当 Rustacean 们提及 Rust 中的 “字符串” 时,他们可能指的要么是 `String`,或者是字符串切片 `&str` 类型,而不单是这两种类型之一。虽然这一小节主要是有关 `String`,但这两种类型在 Rust 的标准库中都大量使用,并且 `String` 和字符串切片都是 UTF-8 编码的。
|
||||
|
||||
|
||||
我们将首先定义出所谓 *字符串* 的含义。Rust 的核心语言中,只有一种字符串类型,即通常以其借用形式 `&str` 出现的字符串切片 `str`。在第 4 章我们曾谈到过 [*字符串片切片*](../ownership/the_slice_type.md#字符串切片),他们是对存储在别处的 UTF-8 编码字符串数据的一些引用。例如,字符串的字面值,就存储在程序的二进制文件中,而因此属于一些字符串的切片。
|
||||
|
||||
|
||||
所谓 `String` 类型,则是由 Rust 的标准库提供,而未被编码到核心语言,是种可增长、可变、有所有权、UTF-8 编码的字符串类型。当 Rust 公民提及 Rust 中的 “字符串” 时,他们可能指的是 `String` 或字符串切片的 `&str` 类型,而不单是其中一种类型。虽然本节主要讨论 `String`,但这两种类型在 Rust 的标准库中都有大量使用,同时 `String` 和字符串切片均为 UTF-8 编码的。
|
||||
|
||||
|
||||
## 创建一个新的 `String`
|
||||
|
||||
对 `Vec<T>` 的许多相同操作对 `String` 也可使用,因为 `String` 实际上是作为字节矢量的封装器实现的,不过带有一些额外的保证、限制及功能。`Vec<T>` 和 `String` 下以同一方式工作的函数示例,便是创建出一个实例的 `new` 函数,如下清单 8-11 所示。
|
||||
## 创建新的 `String`
|
||||
|
||||
由于 `String` 实际上是作为对字节矢量的封装器实现的,并有着一些额外的保证、限制及功能,因此可用于 `Vec<T>` 的许多相同操作也可用于 `String`。一个在 `Vec<T>` 和 `String` 上工作方式相同的函数示例,便是创建实例的 `new` 函数,如下清单 8-11 中所示。
|
||||
|
||||
<a name="listing_8-11"></a>
|
||||
```rust
|
||||
let mut s = String::new();
|
||||
```
|
||||
|
||||
*清单 8-11:创建一个新的空 `String`*
|
||||
**清单 8-11**:创建一个新的空 `String`
|
||||
|
||||
|
||||
这行代码会创建出一个名为 `s` 的新空字符串,然后我们就可以向其中加载数据。通常情况下,我们会使用一些咱们开始该字符串的初始数据。为此,我们会使用 `to_string` 方法,该方法适用于任何实现了 `Display` 特质的类型,正如字符串字面量那样。下面清单 8-12 展示了两个示例。
|
||||
这行代码创建了个名为 `s` 的新空字符串,随后我们可以加载数据到其中。通常,我们将有一些我们打算以其开始字符串的初始数据。为此,我们会使用 `to_string` 方法,其在任何实现了 `Display` 特质的类型上都可用,字符串字面量便如此。下面清单 8-12 展示了两个示例。
|
||||
|
||||
|
||||
<a name="listing_8-12"></a>
|
||||
```rust
|
||||
let data = "初始内容";
|
||||
|
||||
let s = data.to_string();
|
||||
|
||||
// 该方法同样直接工作于字面值之上
|
||||
// 该方法直接在字面值之上也工作
|
||||
let s = "初始内容".to_string();
|
||||
```
|
||||
|
||||
*清单 8-12:使用 `to_string` 方法从某个字符串字面值创建出 `String`*
|
||||
**清单 8-12**:使用 `to_string` 方法从字符串字面值创建 `String`
|
||||
|
||||
这段代码会创建出一个包含 `初始内容` 的字符串。
|
||||
|
||||
|
||||
我们还可以使用函数 `String::from`,从某个字符串字面量创建出字符串。下面清单 8-13 中的代码,等同于清单 8-12 中使用 `to_string` 的代码。
|
||||
这段代码会创建一个包含 `初始内容` 的字符串。
|
||||
|
||||
我们还可使用函数 `String::from` 从字符串字面量创建 `String`。下面清单 8-13 中的代码与清单 8-12 中使用 `to_string` 的代码等价。
|
||||
|
||||
|
||||
<a name="listing_8-13"></a>
|
||||
```rust
|
||||
let s = String::from("初始内容");
|
||||
```
|
||||
|
||||
*清单 8-13:使用 `String::from` 函数,从某个字符串字面值创建出 `String`*
|
||||
**清单 8-13**:使用 `String::from` 函数从字符串字面值创建 `String`
|
||||
|
||||
|
||||
由于字符串的用途非常广泛,我们可以使用许多不同的字符串通用 API,从而为我们提供了大量选择。其中有些看起来是多余的,但他们都有自己的用武之地!在这个示例中,`String::from` 和 `to_string` 做的是同一件事,所以咱们选择哪个只是风格与可读性的问题。
|
||||
由于字符串的用途非常广泛,我们可以使用许多不同的字符串通用 API,从而提供给我们很多选择。其中一些 API 看似多余,但他们都有他们的用处!在这一情形下,`String::from` 和 `to_string` 完成同一件事,因此咱们选择哪个取决于样式与可读性。
|
||||
|
||||
请记住,字符串是 UTF-8 编码的,因此我们可以在其中包含任何正确编码的数据,如下清单 8-14 所示。
|
||||
请记住,字符串都是 UTF-8 编码,因此我们可以在他们中包含任何正确编码的数据,如下清单 8-14 中所示。
|
||||
|
||||
<a name="listing_8-14"></a>
|
||||
```rust
|
||||
let hello = String::from("السلام عليكم");
|
||||
let hello = String::from("Dobrý den");
|
||||
@@ -79,16 +79,14 @@
|
||||
let hello = String::from("👋");
|
||||
```
|
||||
|
||||
*清单 8-14:以字符串存储不同语言的问候语*
|
||||
**清单 8-14**:以字符串存储不同语言的问候语
|
||||
|
||||
所有这些都是有效的 `String` 值。
|
||||
|
||||
|
||||
## 更新字符串
|
||||
|
||||
在咱们向某个 `String` 中压入更多数据时,其大小和内容都会发生变化,就像 `Vec<T>` 的内容一样。此外,咱们还可以方便地使用 `+` 运算符或 `format!` 宏,连接多个 `String` 值。
|
||||
|
||||
|
||||
当咱们压入更多数据到 `String` 中时,其大小会增加且其内容会变化,就像 `Vec<T>` 的内容一样。此外,咱们可以方便地使用 `+` 运算符或 `format!` 宏连接 `String` 值。
|
||||
|
||||
### 使用 `push_str` 与 `push` 追加内容到某个 `String`
|
||||
|
||||
|
||||
Reference in New Issue
Block a user