Aravinda (cc’ing rust-dev)-

It seems like you are trying to program in Rust as if it were a 
dynamically-typed language, or one with runtime-type reflection (i.e. like 
Java).  At least, that is my best guess at where your misunderstanding lies.

All functions in Rust, even generic ones, need to have their types resolved at 
compile-time.  A generic function can have different concrete types substituted 
in for its type parameters at different call-sites, but in the end, a 
particular call-site needs to resolve to a single type at compile-time; the 
type cannot be left for later resolution at program runtime.

In a signature like your:

    fn get_value(settings:HashMap<String, MyTypes>, key: &'static str) -> T;

the particular instance of `MyTypes` that is returned will depend on which 
`key` is passed in; therefore, the `T` above could only be dynamically 
determined based on the runtime computation.  It inherently cannot be resolved 
at compile-time, and therefore it is not statically typed.

----

Rust is not alone in offering this kind of generic types; many programming 
languages use a similar logic for determining types at compile time.  It just 
gets fuzzy if one is used to languages that maintain types at runtime and do 
not enforce restrictions like the one I outlined above.

These type systems are often said to offer “parametric polymorphism”; I mention 
that solely to give you some guidance for a term to search for when goggling 
this subject.  (Though I will say up front that a lot of the results you get on 
this topic can be very academic and language research-oriented.)

Here is a tutorial that may help you get a handle on the concepts here:

  http://lucacardelli.name/Papers/BasicTypechecking.pdf

(Yes, it is from 1987.  I think that is why it probably one of the better 
descriptions I was able to find quickly: At that time, these ideas were not as 
widely popularized as they were today, so Cardelli took his time explaining the 
notions and assumed little about the audience.)

rust-dev members: If others know of freely available introductions to this 
topic, I’m all ears; I just didn’t see any obvious winners in my searches.

Cheers,
-Felix


On 22 Jul 2014, at 14:24, Aravinda VK <hallimanearav...@gmail.com> wrote:

> Sorry for the incomplete mail.
> 
> What I wanted is,
> get_value(MyStr("Rust".to_str())) returns String,
> get_value(MyBool(true)) returns bool and,
> get_value(MyInt(100)) returns int
> 
> I was trying to store generic value in hashmap, as in the example below,
> 
> use std::collections::hashmap::HashMap;
> 
> #[deriving(Show)]
> enum MyTypes{
>     MyBool(bool),
>     MyStr(String),
>     MyInt(int)
> }
> 
> fn main(){
>     let mut settings:HashMap<String, MyTypes> = HashMap::new();
> 
>     settings.insert("port".to_str(), MyInt(8000));
>     settings.insert("name".to_str(), MyStr("Rust".to_str()));
>     settings.insert("enabled".to_str(), MyBool(true));
> 
>     println!("{}", settings);
> }
> 
> So to get the value out of hashmap, I need a generic function which checks 
> the respective type and returns value. Some thing like
> 
> fn get_value(settings:HashMap<String, MyTypes>, key: &'static str) -> T{
>     match settings.get(&key) {
>         MyBool(x) => x,
>         MyStr(x) => x,
>         MyInt(x) => x
>     }
> }
> 
> But I don't know how to make this work.
> 
> Thanks.
> 
> 
> 
> On Tue, Jul 22, 2014 at 4:55 PM, Felix S. Klock II <pnkfe...@mozilla.com> 
> wrote:
> Aravinda (cc’ing rust-dev)-
> 
> You didn’t show us exactly what you had tried to do to get your code to work, 
> nor did you really describe what it is you want here.
> 
> E.g. you seem to want `get_value(MyBool(true))` to return a boolean, but 
> since `MyBool` belongs to the `MyTypes` enum, that implies that `get_value` 
> when applied to any variant of `MyTypes` (including `MyInt` or `MyStr`) 
> should also return a boolean … does that seem right to you?
> 
> In any case, I suspect the missing piece of the puzzle for you is that you 
> need to write an `impl` for the type in question.  I.e. something along the 
> lines of:
> 
> impl MyTypes {
>     fn render(&self) -> String {
>         match *self {
>             MyBool(x) => format!("{:b}", x),
>             MyStr(ref x) => x.clone(),
>             MyInt(x) => format!("{:d}", x),
>         }
>     }
> }
> 
> (except revised from an Impl for the type to being an impl of some trait for 
> the type).
> 
> Here is a link to a playpen with your code, and with a couple of example 
> `impl`s for enums (like the one above) tossed in, including an impl of one 
> instance of your `Value<S>` trait.
> 
>   http://is.gd/RofN9R
> 
> There is more discussion of writing implementations that also provides an 
> example with a simpler enum) in the Rust tutorial, see:
> 
>   http://doc.rust-lang.org/tutorial.html#methods
> 
> Cheers,
> -Felix
> 
> On 22 Jul 2014, at 11:45, Aravinda VK <hallimanearav...@gmail.com> wrote:
> 
> > Hi,
> >
> > I am trying to create a generic function to return value depending on the 
> > enum passed. But I don't know to create a generic trait for enum.
> >
> > In following example, print_value works but I don't know how I can write a 
> > generic get_value function to get value from enum.
> >
> > #[deriving(Show)]
> > enum MyTypes{
> >     MyBool(bool),
> >     MyStr(String),
> >     MyInt(int)
> > }
> >
> > fn print_value(arg: MyTypes){
> >     match arg{
> >         MyBool(x) => println!("Bool: {}", x),
> >         MyStr(x) => println!("String: {}", x),
> >         MyInt(x) => println!("Int: {}", x),
> >     }
> > }
> >
> >
> > fn main(){
> >     print_value(MyBool(true));
> >
> >     // Following lines not working, how to write get_value func?
> >     // let a: bool = get_value(MyBool(true));
> >     // println!("{}", a);
> > }
> >
> >
> > In case of struct it is simple,
> >
> > struct MyInt {
> >     value: int
> > }
> >
> > struct MyBool{
> >     value: bool
> > }
> >
> > trait Value<S>{
> >     fn get(&self) -> S;
> > }
> >
> > impl Value<int> for MyInt{
> >     fn get(&self) -> int{
> >         self.value
> >     }
> > }
> >
> > impl Value<bool> for MyBool{
> >     fn get(&self) -> bool{
> >         self.value
> >     }
> > }
> >
> > fn get_value<S, T: Value<S>>(arg: T) -> S{
> >     arg.get()
> > }
> >
> > fn main(){
> >     let a: bool = get_value(MyBool{value: true});
> >     println!("{}", a);
> >
> >     let b: int = get_value(MyInt{value: 100});
> >     println!("{}", b);
> > }
> >
> > Please help in writing generic function for enum.
> >
> >
> >
> > --
> > Regards
> > Aravinda | ಅರವಿಂದ
> > http://aravindavk.in
> > _______________________________________________
> > Rust-dev mailing list
> > Rust-dev@mozilla.org
> > https://mail.mozilla.org/listinfo/rust-dev
> 
> 
> 
> 
> -- 
> Regards 
> Aravinda | ಅರವಿಂದ 
> http://aravindavk.in

_______________________________________________
Rust-dev mailing list
Rust-dev@mozilla.org
https://mail.mozilla.org/listinfo/rust-dev

Reply via email to