1

I am very used to Java where I can create an ArrayList to hold multiple objects, but I don't know how to do it in C++.

I have 6 different objects: WebcamData UltrasonicData KinectData ImuData GpsData SickData

I need to hold an instance of each in one array.

In java it would be like:

ArrayList array = new ArrayList();
array.add(new WebcamData);
array.add(new UltrasonicData);

etc...

How can I make a similar array in C++?

Thank you

user1028641
  • 287
  • 1
  • 5
  • 15

6 Answers6

11

Use std::vector<boost::any>:

std::vector<boost::any> miscArray;
miscArray.push_back(Apple());
miscArray.push_back(Onion());
miscArray.push_back(Bear());
miscArray.push_back(Beer());

Read the documentation:

The implementation of boost::any is very simple, which means you can implement it yourself if you cannot use Boost library.

A good topic at Stackoverflow:

Community
  • 1
  • 1
Nawaz
  • 353,942
  • 115
  • 666
  • 851
  • A hint might be good that you need the boost library for that. – juergen d Jan 23 '12 at 17:08
  • This is a good answer in some contexts, but in this, all of his stuff is called `*data`. It looks like he needs an interface. – Mooing Duck Jan 23 '12 at 17:19
  • 1
    @MooingDuck: Everything is data in the end; even `Onion` and `Bear` in my example are data. In the question, his data seems to be unrelated, and there is no much info which I can use to give better answer. – Nawaz Jan 23 '12 at 17:24
  • 1
    I would argue they seem like they are data sources and would have similar interfaces. If not, then the other part of the answer is that they do not belong in the same container. – Mooing Duck Jan 23 '12 at 17:26
4

I guess that if you need to put some objects in the same array that means that these objects should represent something common, so I suggest you to use interface and implement it in all of your classes which will be added at the same list. In java instead of this interface you have the Object class. So finally your code will be like:

class IMyInterface {
public:
    virtual ~IMyInterface() {};
    virtual char* getData()=0;
};
class WebcamData : IMyInterface {
    /*private stuff*/
public:
    /*public stuff*/
    virtual char* getData() {/*getData code*/};
    virtual ~WebcamData() {/*destructor code*/};
}

std::vector< IMyInterface* > _myVector;
Mooing Duck
  • 64,318
  • 19
  • 100
  • 158
AlexTheo
  • 4,004
  • 1
  • 21
  • 35
  • +1 Classic case for polymorphism. They're all called xxxData, there's a pretty good chance they can all derive from one class and you can store shared_ptrs in a vector. – pezcode Jan 23 '12 at 17:27
2

C++ does not come with a build-in typeless container or any typeless mechanism (short of void*). The usual solution is to use boost::any. This assumes that there really is no common base class between those types. If there is, you can use a vector of pointers to that base.

pmr
  • 58,701
  • 10
  • 113
  • 156
0

If all values you will add are pointers, you can use a void pointer:

std::vector<void *> myVector;
fbafelipe
  • 4,862
  • 2
  • 25
  • 40
0

Here's another implementation.

 #include <iostream>

class KinectDevices 
{
     public:
      virtual void On(void) {std::cout << "Kinect is on " << '\n';}
      virtual ~KinectDevices() {std::cout << "  is off" << '\n';}
};

class kinWebcamData: public KinectDevices 
{
     public: 
      void On(void) {std::cout << "Webcam  is on" << '\n';}
      ~kinWebcamData(void) { std::cout << "Webcam  " << ' ';}
};

class kinUltrasonicData: public KinectDevices 
{
     public: 
      void On(void) {std::cout << "Ultrasonics is on" << '\n';}
      ~kinUltrasonicData(void) {std::cout << "Ultrasonic  " << ' ';}
};

int main(void)
{
    const int count = 2;
    // create object array
    KinectDevices *particularKinectDeviceFunction[count];

    // create instances of WebcamData()  UltrasonicData()  KinectData() 
    kinWebcamData *WebcamData = new kinWebcamData();
    kinUltrasonicData  *UltrasonicData = new kinUltrasonicData();

    //put objects into array
    particularKinectDeviceFunction[0] = WebcamData;
    particularKinectDeviceFunction[1] = UltrasonicData;

    particularKinectDeviceFunction[0]->On();
    particularKinectDeviceFunction[1]->On();

    delete WebcamData;
    delete UltrasonicData;

    std::cout<<" \nPress any key to continue\n";
    std::cin.ignore();

    return 0;

}

Output:

Webcam  is on
Ultrasonics is on
Webcam     is off
Ultrasonic     is off


Press any key to continue
0

I don't think the answers would be complete without mentioning boost::variant.

You could use

typedef boost::variant<WebcamData,UltrasonicData,KinectData,ImuData,GpsData,SickData> Data

and then keep them in a std::vector<Data>

You could then process the elements using visitors in a very type safe manner.

enobayram
  • 4,650
  • 23
  • 36