簡體   English   中英

如何通過使用迭代器將對象映射到元組的向量?

[英]How to reverse map of objects to vector of tuples by using an iterator?

使用迭代器將HashMap<String, String>轉換為Vec<(String, Vec<String>)>的最簡單方法是什么? 我想反轉地圖。

我試圖使用iter()方法,但不知道如何在以下情況下執行正確的map閉合實現以收集值:

fn get_aliases(&self) -> Vec<(String, Vec<String>)> {
    let mut aliases: HashMap<String, String> = HashMap::new();
    aliases.insert("a".to_owned(), "test".to_owned());
    aliases.insert("b".to_owned(), "test".to_owned());
    aliases.insert("c".to_owned(), "test2".to_owned());

    aliases.iter().map(|(ref a, ref c)| {
        // what to do here?
    }).collect()

    // the expected return value is:
    // [("test", ["a", "b"]), ("test2", ["c"])]
}

此函數將返回一個向量,該向量說明哪些String鍵屬於某個對象。

我可以用forfind編寫很多代碼,但是在我看來這效率較低,我認為有一種方法可以僅使用迭代器來實現。

我可以用forfind編寫很多代碼,但是在我看來這效率較低,我認為有一種方法可以僅使用迭代器來實現。

我不會調用很多代碼,並且請記住for循環在迭代器上運行 我還沒有進行任何基准測試,但是這要簡單得多,並且我希望它會表現得更好:

use std::collections::HashMap;

fn get_aliases(aliases: HashMap<String, String>) -> Vec<(String, Vec<String>)> {
    let mut x = HashMap::new();

    for (k, v) in aliases {
        x.entry(v).or_insert_with(Vec::new).push(k)
    }

    x.into_iter().collect()
}

fn main() {
    let mut aliases = HashMap::new();
    aliases.insert("a".to_owned(), "test".to_owned());
    aliases.insert("b".to_owned(), "test".to_owned());
    aliases.insert("c".to_owned(), "test2".to_owned());

    println!("{:?}", get_aliases(aliases));
}

它並不瑣碎,當然不像其他一些提供必要功能的流庫那樣瑣碎。

您可以使用itertools板條箱的group_by按某個鍵對元素進行分組。 但是,它僅對相鄰元素進行分組,因此您必須先對其進行排序。 這是我的結果:

impl A {
    pub fn get_aliases(&self) -> Vec<(String, Vec<String>)> {
        // Get a Vec of string references for sorting. Reverse element
        // order for clarity.
        let mut v = self.aliases.iter()
            .map(|(a, c)| (&c[..], &a[..])).collect::<Vec<_>>();
        v.sort_by_key(|t| t.0); // Make identical keys adjacent.
        let g = v.into_iter().group_by(|t| t.0); // Create grouping.
        g.into_iter()
            .map(|(key, group)| // key is the str with the key
                                // group is a subiterator that just visits
                                // elements with that key, Item=&(&str,&str)
                (key.to_string(), // result is a tuple of the key as String
                 group.map(|t| t.1.to_string()).collect())
                   // and the subiterator turned into a Vec<String>
                )
            .collect() // finally, turn Iterator<Item=(String, Vec<String>) into Vec
    }
}

回到最初的問題,如果Object是,則還有一個問題,即Arc<Object>僅是PartialEqgroup_by所需)。 Ord相同(需要sort_by_key )。 如果無法通過這種方式比較Object類型,並且要使用指針標識,則中間向量將需要在Arc周圍存儲一些使用指針值進行比較的新型包裝器。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM