tags:

views:

100

answers:

4

I have created a structure of different data types and i want to return each type of data. does this can be done using a function template which takes a different data argument not included in structure or no arguments?

I have something like this,

struct mystruct{
int _int;
char _c;
string _str
};

In function template(int i)
{
     mystruct s;

      switch (getInput)
     {
      case 1:
        return s._int;
      case 2:
        return s._c;
      case 3:
        return s._str;
   }   
} 

void main()  

{
   int getInput = 1;
   //pass getInput value to function template
}
+5  A: 

Yes:

template<class T>
T f() {
  return 0; // for the sake of example
}

int main() {
  return f<int>(); // specify the template parameter
}

template<class T>
vector<T> another_example();
// use another_example<int>() which returns a vector<int>
Roger Pate
That's what I was thinking.
GMan
We'll see if I interpreted him correctly.. :)
Roger Pate
I found another way of reading it, I think. :) It's on, now.
GMan
I bet it has nothing with templates to do at all ;) I'll give you +1 anyhow.
Skurmedel
+1  A: 

The following is building of GMan's (now deleted) interpretation of your very confusing question:

struct some_data
{
    int i;
    char c;
    std::string s;
};

template< typename T > struct Getter;
template<> struct Getter<int> { static int& get(some_data& data) {return data.i} };
template<> struct Getter<char> { static char& get(some_data& data) {return data.c} };
template<> struct Getter<std::string> { static std::string& get(some_data& data) {return data.s} };

template< typename T >
inline T get(some_data& data) {return Getter<T>::get(data);}

I'm not sure. though, whether this is what you were asking for.

sbi
+1 Almost exactly what I was writing up. (P.S. I'm deleting my answer since yours is best, you should remove the link to mine.)
GMan
I'm not sure this is right, because it seems he wants to determine the type at runtime (I'm basing this on *getInput* meaning input from the user); but as we know, that isn't possible. You can also specialize *get* directly, since it doesn't require partial specialization.
Roger Pate
I guess I would go with using the return f<typename>(); specifying the return type at compile time.
Dave18
+1  A: 

What I understand is the following: I want to create a function whose return type depends on its parameter(s). Well, technically, you can't.

  1. When those return types are classes with a common ancestor, you could return a pointer to that ancestor. It's not quite the same thing, but it works. Unfortunately, two of the return types are char and int, which are not classes in first place.

  2. When those return types are plain old data types, you could return a tagged union. Unfortunately, one of the return types is std::string, which is not a plain old data type.

  3. A solution that works with any type but is incredibly hacker-ish is to use void*. Well, unfortunately, void* is error-prone. Whoever maintains your code will curse you forever if you use void*.

  4. A final solution (pun not intended) that works is to use boost::variant. It's quite complicated, but at least it's safe (unlike void*), because type errors can be checked at compile time.

Eduardo León
A: 

Here is another interpretation that doesn't use templates:

struct some_data
{
    int i;
    char c;
    std::string s;

    void get(int& value) const
         { value = i; }
    void get(char& value) const
         { value = c; }
    void get(& value) const
         { value = s; }
};

// ...
some_data received_data;
int k;
received_data.get(k);
//...
received_data.s = "Hello";
std::string world;
received_data.get(world);
std::cout << world << std::endl;

The compiler will generate the correct method calls based on the type of the argument. This can be translated into non-member functions:

void Get_Some_Data(char& value, const some_data& sd)
{
    value = sd.c;
    return;
}


void Get_Some_Data(int& value, const some_data& sd)
{
    value = sd.i;
    return;
}

void Get_Some_Data(std::string& value, const some_data& sd)
{
    value = sd.s;
    return;
}

//...
char f;
Get_Some_Data(f, received_data);
Thomas Matthews
Can simplify to http://codepad.org/gftYzDSI.
Roger Pate