vectors of vectors of different types...
CodeGuru Home VC++ / MFC / C++ .NET / C# Visual Basic VB Forums Developer.com
Results 1 to 14 of 14

Thread: vectors of vectors of different types...

Hybrid View

  1. #1
    Join Date
    Jul 2010
    Posts
    3

    vectors of vectors of different types...

    Hi,

    So my problem is that I need to create a data table in which each column is a vector that contains some sort of data that is read in from a file. The problem is that the table could have any dimensions, and each column can be one of many types (string, int, double, etc.). I would like to know if there is a way to create this object that I want. Right now I am attempting to do it using a template class:

    Code:
     template <typename T2>
    class asciiColumn
    {
        vector<T2> vec;
        public:
            asciiColumn(vector<T2>);
            vector<T2> read();
    
            asciiColumn (vector<T2> invec)
            {
                vec = invec;
            }
            
            asciiColumn() {}
    
            vector<T2> read()
            {
                return vec;
            }
    };
    The problem with this is that to instantiate a vector of asciiColumns I have to specify the type that asciiColumn should contain, and that defeats the purpose.

    Any help with this solution or other proposed solutions would be much appreciated.

    Thanks, Tommy

  2. #2
    Join Date
    Jan 2006
    Location
    Singapore
    Posts
    6,580

    Re: vectors of vectors of different types...

    What is stopping you from say, storing the data read as strings, and then converting to the desired type when needed?
    C + C++ Compiler: MinGW port of GCC
    Build + Version Control System: SCons + Bazaar

    Look up a C/C++ Reference and learn How To Ask Questions The Smart Way
    Kindly rate my posts if you found them useful

  3. #3
    Join Date
    Jul 2010
    Posts
    3

    Re: vectors of vectors of different types...

    Haha nothing i suppose. I'm a little embarrassed that I didn't think of that. That would also make reading in from files a lot easier... thanks!

  4. #4
    Join Date
    Jul 2002
    Location
    Portsmouth. United Kingdom
    Posts
    2,726

    Re: vectors of vectors of different types...

    Another way would be to create a base value class and derive value types from it. The vector would store pointers to base types. This would require you to manage the allocation and destruction of the elements.

    Code:
    struct Value
    {
    };
    
    struct Int_Value : public Value
    {
        int value;
    };
    
    struct Double_Value : public Value
    {
        double value;
    };
    
    struct String_Value : public Value
    {
        std::string value;
    };
    
    vector<Value *> vector_of_values;
    "It doesn't matter how beautiful your theory is, it doesn't matter how smart you are. If it doesn't agree with experiment, it's wrong."
    Richard P. Feynman

  5. #5
    Join Date
    Aug 2012
    Posts
    10

    Re: vectors of vectors of different types...

    I know this is an old post. I came across this code from the previous post in this thread and tried to use it. But I am having problems with accessing the value variables in the structs.

    Code:
    struct Value
    {
    };
    
    struct Int_Value : public Value
    {
        int value;
    };
    
    struct Double_Value : public Value
    {
        double value;
    };
    
    struct String_Value : public Value
    {
        std::string value;
    };
    
    vector<Value *> vector_of_values;
    
    // I added the code below to test
    vector_of_values.resize(2);
    vector_of_values.at(0) = new Int_Value;
    vector_of_values.at(1) = new String_Value;
    
    // Everything compiles till here. Problem is when I try to access vector_of_values.at(0) or vector_of_values.at(1)
    
    vector_of_values.at(0)->value = 3; // This gives an error
    How do I access the value variable of Int_Value or String_Value from vector_of_values?

    Using Visual Studio 2008. Win 7.

  6. #6
    Join Date
    Jun 2015
    Posts
    65

    Re: vectors of vectors of different types...

    Quote Originally Posted by drax22 View Post
    How do I access the value variable of Int_Value or String_Value from vector_of_values?
    I don't know what you're ultimately trying to accomplish but have you considered using a separate vector for each different value? One int vector, one double vector, one string vector, etcetera. Storing different values in the same vector means the individual types will be lost and then has to be recovered somehow. It's possible but most straightforward is to avoid losing type information in the first place.

    If you still decide you want just one vector the object oriented (OO) way is to make the Value base class polymorphic. In that case the derived classes in the vector are never asked to reveal the actual type of the value they hold. Instead they are asked to perform stuff using their values but without anyone needing to know what exact type that might be. An ambitious variation on this theme is the so called Visitor design pattern (which has been mentioned).

    If you don't want to use OO polymorphism the remaining option is to "identify type and downcast". Here the derived value classes must be marked somehow to compensate for the lost type information. Either you do it yourself by adding a "tag" field representing the lost types, or you ask the runtime system by way of the typeid operator. Using an established feature like Boost.Any may make this approach more palatable (which has also been mentioned).
    Last edited by tiliavirga; August 19th, 2015 at 02:07 AM.

  7. #7
    Join Date
    Jan 2006
    Location
    Singapore
    Posts
    6,580

    Re: vectors of vectors of different types...

    Quote Originally Posted by drax22
    How do I access the value variable of Int_Value or String_Value from vector_of_values?
    The problem is that you have a vector of pointers to Value. The Value class does not have a member named value. Hence, you need to cast the pointer to Value to be a pointer to whatever derived class is the underlying class of the object that the pointer points to. Unfortunately, you presumably do not know what that derived class is, so you would need to try dynamic_cast for all derived classes until dynamic_cast returns a non-null pointer... but of course if another derived class is defined, you need to update all the code where these dynamic_casts are used.

    Instead of doing such a series of dynamic_casts, perhaps you could opt to implement the Visitor pattern, but it has its pros and cons too. Oh, and besides, the Value class should have a virtual destructor in case you attempt to use delete or delete[] on a pointer to Value that points to a derived class object.

    Instead of what has been discussed in this thread, you could also look to see if Boost.Any would work for you.
    C + C++ Compiler: MinGW port of GCC
    Build + Version Control System: SCons + Bazaar

    Look up a C/C++ Reference and learn How To Ask Questions The Smart Way
    Kindly rate my posts if you found them useful

  8. #8
    Join Date
    Apr 2000
    Location
    Belgium (Europe)
    Posts
    4,587

    Re: vectors of vectors of different types...

    that is what templates do... decide the actual types AT COMPILE TIME.

    You seem to want to decide the type at runtime. That would require a type that can store one of many types, akin to the COM VARIANT or boost::variant

  9. #9
    Join Date
    Aug 2012
    Posts
    10

    Re: vectors of vectors of different types...

    I realized the mistake I made about not specifying the type at compile time. If I change the line to

    Code:
    ((Int_Value *)vector_of_values.at(0))->value = 3;
    This compiles. But this seems to be a messy way of doing this.

    My apologies for the delayed reply, I had gone on vacation.

  10. #10
    Join Date
    Jan 2006
    Location
    Singapore
    Posts
    6,580

    Re: vectors of vectors of different types...

    Have you considered using a relational database engine like SQLite instead? Some of these, like SQLite, can be embedded into your program, and you could use an in-memory database if necessary.
    C + C++ Compiler: MinGW port of GCC
    Build + Version Control System: SCons + Bazaar

    Look up a C/C++ Reference and learn How To Ask Questions The Smart Way
    Kindly rate my posts if you found them useful

  11. #11
    Join Date
    Aug 2012
    Posts
    10

    Re: vectors of vectors of different types...

    How well does SQLite work with Visual C++? I am using VS 2008.

  12. #12
    Join Date
    Dec 2012
    Location
    England
    Posts
    3,470

    Re: vectors of vectors of different types...

    So how would I go about storing the data in this table?
    A simple way of doing this is to store all data as strings and have a type field to indicate whether the row should be treated as chars or as numeric. Something like
    Code:
    struct Rdata
    {
    	bool isNumeric;
    	vector<string> trows;
    };
    
    vector<Rdata> mytable;
    All advice is offered in good faith only. You are ultimately responsible for effects of your programs and the integrity of the machines they run on.

  13. #13
    Join Date
    Aug 2012
    Posts
    10

    Re: vectors of vectors of different types...

    Quote Originally Posted by 2kaud View Post
    A simple way of doing this is to store all data as strings and have a type field to indicate whether the row should be treated as chars or as numeric. Something like
    I thought of doing that, but I have to perform calculations on the rows that have double values. For example I would have to sum up all the double values, about 100,000 of them, in a row. So to do that I would have to convert from string to double and that may not be the fastest way.

    The simplest way I could think of was to have a vector of string and vector of double for each row, but in each row resize only one based on if strings or doubles are in that row.

    Code:
    struct Rdata
    {
    	bool isNumeric;
    	vector<string> txtrows;
    	vector<double> dblrows;
    };
    
    vector<Rdata> mytable;
    
    int main()
    {
        // Create a table with 3 rows and 2 columns. With Row 1 - strings, Row 2 & 3 - doubles
        mytable.resize(3); // Table with 3 rows
        mytable.at(0).txtrows.resize(2);  // Adding two  columns to row 1 as string, dblrows stays empty
        mytable.at(1).dblrows.resize(2);  // Adding two columns to row 2 as double , txtrows stays empty
        mytable.at(2).dblrows.resize(2);  // Adding two columns to row 3 as double, txtrows stays empty
        
        mytable.at(0).txtrows.at(0) = "AAA";
        mytable.at(0).txtrows.at(1) = "BBB";
        
        mytable.at(1).dblrows.at(0) = 123.45;
        mytable.at(1).dblrows.at(1) = 5353.23;
        
        mytable.at(2).dblrows.at(0) = 1.0;
        mytable.at(2).dblrows.at(1) = 2.0;
        
        cout << mytable.at(0).txtrows.at(0) << endl << mytable.at(0).txtrows.at(1) << endl;
        cout << mytable.at(1).dblrows.at(0) << endl << mytable.at(1).dblrows.at(1) << endl;
        cout << mytable.at(2).dblrows.at(0) << endl << mytable.at(2).dblrows.at(1) << endl;
       
       return 0;
    }

Tags for this Thread

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •  


Windows Mobile Development Center


Click Here to Expand Forum to Full Width

This is a Codeguru.com survey!


HTML5 Development Center