【问题标题】:Efficient ways to build new Strings in Rust在 Rust 中构建新字符串的有效方法
【发布时间】:2021-12-15 20:59:41
【问题描述】:

我最近才开始学习 Rust,并且一直在搞乱一些代码。我想创建一个简单的函数,从字符串中删除元音并返回一个新字符串。下面的代码可以运行,但我担心这是否真的是这种语言中有效的典型方法,或者我是否遗漏了什么......

// remove vowels by building a String using .contains() on a vowel array
fn remove_vowels(s: String) -> String {
    let mut no_vowels: String = String::new();
    for c in s.chars() {
        if !['a', 'e', 'i', 'o', 'u'].contains(&c) {
            no_vowels += &c.to_string();
        }
    }
    return no_vowels;
}

首先,使用to_string() 构造一个新的字符串,然后使用& 借用似乎不合适。有没有更简单的方法将字符附加到字符串,或者这是唯一的方法?还是我应该完全重写它并使用循环按长度而不是字符数组遍历输入的字符串?

另外,我被告知在 Rust 中很流行不使用 return 语句,而是让最后一个表达式从函数中返回值。此处是否需要我的 return 语句,还是有一种更简洁的方法可以按照约定返回该值?

【问题讨论】:

标签: string rust character borrow-checker


【解决方案1】:

如果您像示例一样使用原始 String,则可以使用 retain() 就地删除元音,这将避免分配新字符串:

fn remove_vowels(mut s: String) -> String {
    s.retain(|c| !['a', 'e', 'i', 'o', 'u'].contains(&c));
    s
}

playground 上查看它。旁注:您可能还需要考虑大写元音。

【讨论】:

    【解决方案2】:

    您可以在字符迭代器上使用collect 来创建字符串。您可以使用filter 过滤掉不需要的字符。

    // remove vowels by building a String using .contains() on a vowel array
    fn remove_vowels(s: &str) -> String {
        s.chars()
            .filter(|c| !['a', 'e', 'i', 'o', 'u'].contains(c))
            .collect()
    }
    

    playground

    如果这是在性能关键区域,那么由于您知道要删除的字符是 utf8 中的单个字节,因此可以直接从字节中删除它们。这意味着你可以写类似的东西

    fn remove_vowels(s: &str) -> String {
        String::from_utf8(
            s.bytes()
                .filter(|c| ![b'a', b'e', b'i', b'o', b'u'].contains(c))
                .collect()
        ).unwrap()
    }
    

    哪个可能更有效率。 playground

    【讨论】:

    • 同样不用消耗输入字符串,取&str代替
    猜你喜欢
    • 1970-01-01
    • 2017-08-22
    • 2018-12-01
    • 2012-02-22
    • 1970-01-01
    • 2013-04-01
    • 2019-01-16
    • 1970-01-01
    • 2011-11-04
    相关资源
    最近更新 更多