假設我想將abc'xyz?'zzz'at every之類的字串拆分'為 Vec<String>,但如果字符前面有?. 我想在沒有正則運算式環視的情況下實作這一點,因為我不能相信輸入。
我可以假設,輸入是 UTF8 兼容的。
在 Rust 中實作這一目標的最快(并且可能是最節省記憶體的方式)是什么?
如果下一個 Char 是 ,我認為迭代字串并將子字串保存到 var 中',但當前 Char 不是?通過 Char 比較。然后我會通過移動將該 var 的值推送到 Vec<String> 中。
這是一個好主意,還是有更有效(時間和記憶體方面)的方法來實作這一目標?
uj5u.com熱心網友回復:
實作這一點最慣用的方法是將其變成一個實作Iterator,獲取&str和生產&str。
這是一個示例實作,它假定'輸入字串的尾隨不應在其后產生空元素,空字串也不應產生任何元素。請注意,沒有復制,因為我們只是在處理字串切片。如果你想產生 aVec<String>那么你可以通過將迭代器映射到 來做到這一點str::to_owned。( .map(str::to_owned).collect::<Vec<_>>())
use std::str::CharIndices;
// A verbose name for an oddly specific concept.
struct SplitStringAtCharNotFollowingCharIterator<'a> {
delimiter: char,
exception: char,
text: &'a str,
chars: CharIndices<'a>,
}
impl<'a> SplitStringAtCharNotFollowingCharIterator<'a> {
pub fn new(text: &'a str, delimiter: char, exception: char) -> Self {
Self { delimiter, exception, text, chars: text.char_indices() }
}
}
impl<'a> Iterator for SplitStringAtCharNotFollowingCharIterator<'a> {
type Item = &'a str;
fn next(&mut self) -> Option<&'a str> {
let first = self.chars.next();
let (start, mut prior) = match first {
None => return None,
Some((_, c)) if c == self.delimiter => return Some(""),
Some(v) => v,
};
loop {
prior = match self.chars.next() {
None => return Some(&self.text[start..]),
Some((end, c)) if c == self.delimiter && prior != self.exception =>
return Some(&self.text[start..end]),
Some((_, c)) => c,
}
}
}
}
(游樂場)
使用它來實作您既定目標的示例:
let pieces = SplitStringAtCharNotFollowingCharIterator::new("abc'xyz?'zzz'", '\'', '?')
.map(str::to_owned)
.collect::<Vec<_>>();
但是,如果您實際上不需要擁有的字串或向量,則可以直接使用迭代器,這不需要任何額外的堆分配,因為它分配了原始切片的子切片。
uj5u.com熱心網友回復:
我認為你不需要過度復雜化——一個簡單的 for 回圈就可以了。這也使您可以輕松地準確調整您希望拆分的作業方式,例如包含/排除分隔符,如何處理空匹配項。 操場
fn split(s: &str) -> Vec<String> {
let mut chunks = Vec::new();
let mut cur = String::new();
let mut last_char = None;
for c in s.chars() {
if c == '\'' && last_char != Some('?') {
chunks.push(std::mem::take(&mut cur));
} else {
cur.push(c);
}
last_char = Some(c);
}
chunks.push(cur);
chunks
}
如果你想生成Vec<&str>,你需要做更多的作業來維護對現有字串的參考,但由于我們正在回傳Vec<String>,我們可以簡單地一個接一個地復制字符。
轉載請註明出處,本文鏈接:https://www.uj5u.com/houduan/452503.html
下一篇:這個反向鏈接串列代碼有什么問題?
