Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

function which is able to return different types?

Tags:

c++

I am trying to create a function in c++, I am wondering if I can create it such that it is able to return different types of vectors. e.g based on different case it returns vector string, int, double or ...anything. Is it possible in c++? (I do not want to use overload function with different arg(S) and different returns) I am very new to C++ and my question may seem to be stupid.

here is a piece of my code:

//zero here means intersection

std::vector<??????> findZeros(const mesh::Region& s, char *model) const
{
//Point  
  if( model == "point" )
  {
    std::vector<Vertex> zeros;
    for(Region::pointIterator it = s.beginPoint(); itv != s.endPoint(); ++itv )
    {
      if( abs(Val(*it)) < 1.e-12 )      
      zeros.push_back(*it);
    }
    std::vector<point> zerosP(zeros.begin(), zeros.end());
    return zerosP;
  }
 //line
  else if (EntityS == "line")
  {
    std::vector<line> zerosE;
    std::vector<Point&> PointE;
    for(Region::lineIterator ite = s.beginLine(); ite != s.endLine(); ++ite )
    {
      Line ed = *ite;
        Point P0 = ed.point(0);
        Point P1 = e.point(1);
        if( ......... ) zerosE.push_back(ed);
        else if ( ....... )
        {
         PontE.push_back( P0, P1);
         zerosE.push_back(ed);
        }
      }

//here I want to return "point" or "line with its points" or in upper level our surface. //I want to do all in one function! }

like image 392
user2090491 Avatar asked Jul 15 '13 07:07

user2090491


1 Answers

Templates

Try this:

template <typename T>
std::vector<T> func( /* arguments */ )
{
    std::vector<T> v;
    // ... do some stuff to the vector ...
    return v;
}

You can call this function with different type in this way:

std::vector<int> func<int>( args );
std::vector<double> func<double>( args );

Alternatives

This is one way, if you know the types at compile-time. If you don't know the type at compile-time but at run-time only, then you have different choices:

  1. Use unions. I can only recommend this, if you have very simple C-struct-like types which are called PODs (plain old data) in the C++ standard.
  2. Use some type of variant. For example there is boost::variant from the Boost libraries or QVariant from the Qt library. They are a safe kind of unions on more general types. They also allow some conversions between different types. For example setting something to an integer value will make it possible to read the same value as floating point number.
  3. Use boost::any which can wrap any type but does not allow conversions between them.
  4. Use inheritance and polymorphism. For this case you need a common base class, say Base. Then you create an array of pointers to that base preferably with std::shared_ptrs. So the array type would be std::vector<std::shared_ptr<Base>>. The std::shared_ptr is better than built in pointers in this case because the manage your memory automagically by reference counting.
  5. Use a dynamic language that doesn't care about types and performance.
like image 148
Ralph Tandetzky Avatar answered Oct 19 '22 02:10

Ralph Tandetzky