How do I create a HashMap literal?

2019-01-08 10:56发布

How I can create a HashMap literal in Rust? In Python I can do it so:

hashmap = {
   'element0': {
       'name': 'My New Element',
       'childs': {
           'child0': {
               'name': 'Child For Element 0',
               'childs': {
                   ...
               }
           }
       }
   },
   ...
}

And in Go like this:

type Node struct {
    name string
    childs map[string]Node
}

hashmap := map[string]Node {
    "element0": Node{
        "My New Element",
        map[string]Node {
            'child0': Node{
                "Child For Element 0",
                map[string]Node {}
            }
        }
    }
}

标签: hashmap rust
3条回答
小情绪 Triste *
2楼-- · 2019-01-08 11:04

There isn't a map literal syntax in Rust. I don't know the exact reason, but I expect that the fact that there are multiple data structures that act maplike (such as both BTreeMap and HashMap) would make it hard to pick one.

However, you can create a macro to do the job for you, as demonstrated in Why does this rust HashMap macro no longer work?. Here is that macro simplified a bit and with enough structure to make it runnable in the playground:

macro_rules! map(
    { $($key:expr => $value:expr),+ } => {
        {
            let mut m = ::std::collections::HashMap::new();
            $(
                m.insert($key, $value);
            )+
            m
        }
     };
);

fn main() {
    let names = map!{ 1 => "one", 2 => "two" };
    println!("{} -> {:?}", 1, names.get(&1));
    println!("{} -> {:?}", 10, names.get(&10));
}
查看更多
霸刀☆藐视天下
3楼-- · 2019-01-08 11:13

There is an example of how to achieve this in the documentation for HashMap:

 let timber_resources: HashMap<&str, i32> =
    [("Norway", 100),
     ("Denmark", 50),
     ("Iceland", 10)]
    .iter().cloned().collect();
查看更多
Explosion°爆炸
4楼-- · 2019-01-08 11:28

I recommend the maplit crate.

To quote from the documentation:

Macros for container literals with specific type.

#[macro_use] extern crate maplit;

let map = hashmap!{
    "a" => 1,
    "b" => 2,
};

The maplit crate uses => syntax for the mapping macros. It is not possible to use : as separator due to syntactic the restrictions in regular macro_rules! macros.

Note that rust macros are flexible in which brackets you use for the invocation. You can use them as hashmap!{} or hashmap![] or hashmap!(). This crate suggests {} as the convention for the map & set macros, it matches their Debug output.

Macros

btreemap Create a BTreeMap from a list of key-value pairs

btreeset Create a BTreeSet from a list of elements.

hashmap Create a HashMap from a list of key-value pairs

hashset Create a HashSet from a list of elements.

查看更多
登录 后发表回答