rust - Trouble with Encodable Trait Bounds on Enums and Structs -
taking rust test drive. fun far, i'm uncertain how set trait bounds in instance useful.
failed find implementation of trait serialize::serialize::encodable,std::io::ioerror> t
it seems me need set bound on enumeration list<t: encodable>
. however, compiler gets bit upset when try this.
error: trait bounds not allowed in enumeration definitions
so assumed have put bounds on implementation impl<t:encodable>
, got this...
error: wrong number of type arguments: expected 2 found 0
if that's case, how in rust?
extern crate serialize; use serialize::{ json, encodable }; #[deriving(decodable, encodable)] pub enum list<t> { node(t, box<list<t>>), nil } impl<t> list<t> { fn to_json(&self) -> string { json::encoder::str_encode(self) } }
seems work fine when work don't try encapsulate encoding, since knows int encodable...
let mut list: list<int> = nil; ... let encoded_string = json::encoder::str_encode(&list); println!("{}", encoded_string);
at present, bounds cannot placed on structs , enums. may change, until then, impl
place define constraints.
let’s @ definition of trait: encodable<s: encoder<e>, e>
. s
, e
things complaining about, wanting define them.
now let’s take @ #[deriving(encodable)]
does, compiling code rustc --pretty expanded
, expands attribute.
#![feature(phase)] #![no_std] #![feature(globs)] #[phase(plugin, link)] extern crate std = "std#0.11.0-pre"; extern crate native = "native#0.11.0-pre"; extern crate serialize; use std::prelude::*; use serialize::{json, encodable}; pub enum list<t> { node(t, box<list<t>>), nil, } #[automatically_derived] impl <__s: ::serialize::encoder<__e>, __e, t: ::serialize::encodable<__s, __e>> ::serialize::encodable<__s, __e> list<t> { fn encode(&self, __arg_0: &mut __s) -> ::std::result::result<(), __e> { match *self { node(ref __self_0, ref __self_1) => { let _e = __arg_0; _e.emit_enum("list", |_e| _e.emit_enum_variant("node", 0u, 2u, |_e| { match _e.emit_enum_variant_arg(0u, |_e| (*__self_0).encode(_e)) { ok(__try_var) => __try_var, err(__try_var) => return err(__try_var) }; return _e.emit_enum_variant_arg(1u, |_e| (*__self_1).encode(_e)); })) }, nil => { let _e = __arg_0; _e.emit_enum("list", |_e| _e.emit_enum_variant("nil", 1u, 0u, |_e| { return ::std::result::ok(()); })) } } } } #[automatically_derived] impl <__d: ::serialize::decoder<__e>, __e, t: ::serialize::decodable<__d, __e>> ::serialize::decodable<__d, __e> list<t> { fn decode(__arg_0: &mut __d) -> ::std::result::result<list<t>, __e> { __arg_0.read_enum("list", |_d| _d.read_enum_variant(["node", "nil"], |_d, i| ::std::result::ok(match { 0u => node(match _d.read_enum_variant_arg(0u, |_d| ::serialize::decodable::decode(_d)) { ok(__try_var) => __try_var, err(__try_var) => return err(__try_var) }, match _d.read_enum_variant_arg(1u, |_d| ::serialize::decodable::decode(_d)) { ok(__try_var) => __try_var, err(__try_var) => return err(__try_var) }), 1u => nil, _ => ::std::rt::begin_unwind("internal error: entered unreachable code", "s.rs", 4u) }))) } } impl <t> list<t> { fn to_json(&self) -> string { json::encoder::str_encode(self) } }
yes, messy. shows encodable
implementation , bounds being written. basically, constraints expected written in same way: don’t care specific types, have encoder. this, then, boils down to:
impl<s: encoder<e>, e, t: encodable<s, e>> encodable<s, e> list<t> { fn encode(&self, encoder: &mut s) -> result<(), e> { … } }
Comments
Post a Comment