2015-09-01 2 views
4

У меня есть файл, содержащий объект JSON с неизвестными ключами. Я хотел бы декодировать этот объект в структуру, но не понимаю, как объявить эту структуру.Deserialising JSON object с rustc_serialize: зачем мне нужно реализовывать PartialEq?

extern crate rustc_serialize; 
use rustc_serialize::json; 
use std::collections::BTreeMap; 

#[derive(RustcDecodable, Debug)] 
struct MyStruct { 
    foo: u8, 
    bar: Vec<String>, 
} 

let raw_json = r#"{ 
    "A": { 
     "foo": 2, 
     "bar": ["a", "b"], 
    }, 
    "C": { 
     "foo": 1, 
     "bar": ["c", "d"], 
    }, 
    : 
}"#; 

let j: BTreeMap<String, MyStruct> = json::decode(&raw_json).unwrap(); 
println!("{:?}", j.get("A").unwrap()); 

Следующая ошибка:

error: the trait `core::cmp::PartialEq` is not implemented for the type `MyStruct` [E0277] 
    let j: BTreeMap<String, MyStruct> = json::decode(&raw_json).unwrap(); 
             ^~~~~~~~~~~~ 

бы я должен реализовать Decodable для MyStruct себя тогда?

+0

Вы пытались внедрить 'PartialEq', как предлагает сообщение об ошибке? – Shepmaster

+0

Нет, tbh. Я думал, что ошибка неверна, поскольку это должно быть возможно. Я реализовал 'PartialEq' сейчас, и он работает. Тем не менее, я до сих пор не понимаю, зачем мне это нужно. Ни один из примеров онлайн, похоже, не делает этого. – Kreisquadratur

+0

* для этого структурного равенства должно быть возможно получено * - никакие черты не производятся автоматически, поэтому вам нужно добавить '# [вывод]'. – Shepmaster

ответ

0

Простой ответ, как намекают @Shepmaster является либо реализовать PartialEq черту или пусть это будет получено, как сообщение об ошибке указывает:

#[derive(RustcDecodable, PartialEq, Debug)] 
+0

Вопрос не в том, «как мне исправить это», «зачем мне это нужно. –

+0

(По крайней мере, так я его прочитал) –

+0

@SteveKlabnik Обратите внимание, что вы отвечаете на ОП вопроса^_^ – Shepmaster

3

json::decode определяется как:

pub fn decode<T: Decodable>(s: &str) -> DecodeResult<T> 

Это означает, что при использовании строкового среза он будет пытаться декодироваться в тип, указанный пользователем, если этот тип реализует Decodable. На странице для Decodable, вы можете увидеть все реализации этого, в том числе один для BTreeMap:

impl<K: Decodable + PartialEq + Ord, 
    V: Decodable + PartialEq> 
Decodable for BTreeMap<K, V> 

Это показывает, что для того, чтобы дешифровать к BTreeMap, ключ и значение в карте должны быть PartialEq. Тем не менее, я не совсем понял, почему это действительно необходимо. BTreeMap должен только требовать, чтобы ключ был Ord и не заботился о стоимости вообще. С этой целью я открыл a pull request, чтобы удалить эти границы, и это было принято!^_^Я предполагаю, что это означает, что границы могли быть только опечаткой изначально.

Смежные вопросы