Easy lookup/access to members in "an array" of different datatypes if possible
category: code [glöplog]
But as a former question it would be if its possible to store members of different datatypes in an array without much painstaking work.
As an example of this consider calling a function looking like this:
etc...
The Add function in the class is defined like this:
data is:
TableBase is nothing more than a class with nothing like maybe just a virtual or pure virtual function.
Table is a template class derived TableBase
How can I get the fucking data from the table as the datatype since ive added it in the template function. is it possible with decltype, auto or some casting. im out after simplest design for template to access data in an array. im not sure how such array would work. ideas, directions are welcome.
As an example of this consider calling a function looking like this:
Code:
pointer->Add<char>(150);
pointer->Add<int>(12000);
etc...
The Add function in the class is defined like this:
Code:
template <class T> void Add(T value)
{
table.push_back(new Table<T>(value));
}
data is:
Code:
std::vector <TableBase *> table;
TableBase is nothing more than a class with nothing like maybe just a virtual or pure virtual function.
Table is a template class derived TableBase
How can I get the fucking data from the table as the datatype since ive added it in the template function. is it possible with decltype, auto or some casting. im out after simplest design for template to access data in an array. im not sure how such array would work. ideas, directions are welcome.
you could use a class that serializes datatypes into binary stream, such aas qdatastream.
Wrong programming language. Or wrong usage of chosen programming language.
No, not in C++.
You could try stuff from Boost, such as Boost.Any, though. There, somebody else did the painstaking work for you.
Quote:
But as a former question it would be if its possible to store members of different datatypes in an array without much painstaking work.
No, not in C++.
You could try stuff from Boost, such as Boost.Any, though. There, somebody else did the painstaking work for you.
well if you consider void* as typeless pointer sure you can do it.
but in your case you have to define a set of overload functions for each type you want.
like
int Get();
char Get();
...
and in each return you enforce a type case for that value.
but in your case you have to define a set of overload functions for each type you want.
like
int Get();
char Get();
...
and in each return you enforce a type case for that value.
type cast*
Use the Boost thing or something similar. Or even better: figure out why it is you want this, take a few steps back and devise a different/simpler approach that better befits language.
Sounds like one of those cases where OO nazis would tell you your design is flawed. Methods that work on a Table object should be encapsulated in the Table class, with a common interface defined in TableBase by virtual methods. Then you don't need to know what specific kind of TableBase pointer you're pulling out of the "table" vector. Polymorphism.
If you're happy with your design, though, you should look at typeid and dynamic_cast: RTTI. One gives you run-time type information, the other lets you cast a pointer safely, returning NULL if you're trying to cast to an incompatible type.
If you're happy with your design, though, you should look at typeid and dynamic_cast: RTTI. One gives you run-time type information, the other lets you cast a pointer safely, returning NULL if you're trying to cast to an incompatible type.
doomdoom: i think its something like this i am out after
and i dont understand what Navis said
check how qdatastream (from qt) works. Type it in google. Then have a look at the >> << operators.
Navis: i see. but, i dont like using external libs for this. i hoped i would not mix it with my code.
what doom said.
If it's performance you're looking for, really think twice before using RTTI. Really think twice before using it in any case, as, conceptually, it's really just red tape.
In my experience, whenever you consider using RTTI, your code-design is flawed.
Amen.
"aw hell, it's just a temporary solution!.." :D
You're all crazy folk, what with your "Disable RTTI and exception handling" checkboxes checked and whatnot!
switch language to ruby, and plan ahead for the perfomance hit ;)
ruby+performance = false
I've had a similar problem, and came up with the following solution:
Instead of having one single array with all elements, I came up with a struct:
I know, it looks ugly, but it serves its purpose. You have a "collection" where every element has a different (known!) type.
Instead of having one single array with all elements, I came up with a struct:
Code:
struct MyData
{
enum DataType
{
Float,
Vector,
Whatever,
//...
}
struct DataEntry
{
DataType dataType;
int index;
}
DataEntry* data;
float* floatData;
vector* vectorData;
whatever* whateverData;
//...
}
//...
MyData myData;
for (int i = /*iterate over everything in myData*/)
{
switch(myData.data[i].dataType)
{
case MyData::DataType::Float:
float value = myData.floatData[myData.data[i].index];
//...
break;
case MyData::DataType::Vector:
vector value = myData.vectorData[myData.data[i].index];
//...
break;
case MyData::DataType::Whatever:
//...
break;
}
}
I know, it looks ugly, but it serves its purpose. You have a "collection" where every element has a different (known!) type.
xTr1m: Use a union, like:
You could also rely on RTTI as previously suggested.
Code:
struct DataEntry {
union {
float f;
vector v;
whatever w;
} value;
DataType type;
}
You could also rely on RTTI as previously suggested.
xTrim: I'm using something similar for variant implementation, but instead of storing a heck-a-load of separate variables like in your case, I just go with a void* that contains pointer to variable of described type. Saves a few bytes, especially if you use a lot of variants (as is in my case, where variants define curve segment/curve node values)
haha Tjoppen, right, was just about to say :) people, read your books before coding okay?
kbi: that level of indirection, even if the memory pointed to is magically allocated in a cachefriendly manner, kills babies in their sleep. union the voidptr with atomic types and only use it for bigger objects.
kbi: that level of indirection, even if the memory pointed to is magically allocated in a cachefriendly manner, kills babies in their sleep. union the voidptr with atomic types and only use it for bigger objects.
(i.e. at least try not to point to stuff thats equal/smaller size than the pointer itself)
xTr1m: looks like a waste of C++. Why not Zoidberg:
It's more compact, maintainable and flexible, and it's less error-prone. Problems like this are precisely why C++ supports polymorphism.
Code:
class MyData
{
public:
virtual void process();
}
class MyData_int : public MyData
{
public:
int value;
void process()
{
//...
}
}
class MyData_float : public MyData
{
public:
float value;
void process()
{
//...
}
}
//...
MyData *myDataArray[100];
//...
for (int i = 0; i < 100; ++i)
myDataArray[i]->process();
It's more compact, maintainable and flexible, and it's less error-prone. Problems like this are precisely why C++ supports polymorphism.