Jump to content
  • Advertisement
Sign in to follow this  
Lode

stack used for both floats and ints

This topic is 4831 days old which is more than the 365 day threshold we allow for new replies. Please post a new topic.

If you intended to correct an error in the post then please contact us.

Recommended Posts

For an interpreter written in C++ for an esoteric programming language, I want to have a stack of floating point numbers. So I want it to have the behaviour as if it's a floating point stack that converts floating point numbers to int when needed and converts them back to float when pushing them again. But, the disadvantage of this is the performance loss when you're working with only ints. What's a good way to make this so that it supports both ints and floats, and only converts it when needed, and so that to the user of this stack it seems as if it's floating point all the time?

Share this post


Link to post
Share on other sites
Advertisement
How about using a universal type stack and 1 specific type to store all data?


enum ScriptType { ST_INT = 0, ST_FLOAT, ST_OBJECT };

struct DataType
{
ScriptType Type;
int Integer;
float Float;
void *Object;
};


Then, when pushing the type:

DataType t;
t.Type = ST_INT;
t.Integer = 10;
stack.push(t);


You have both the speed and reusability. It uses some more memory, but it's pretty efficient.

Toolmaker

Share this post


Link to post
Share on other sites
I dunno, I suppose you could make a wrapper structure use a union and a flag to say which type is actually stored (int or float). That seems a bit yucky to me though.

It's hard to say... it might be helpful to first of all prioritise for us what is more important to you... time to insert a value or time to read? Space or speed?

I would also say just program it how you think it should look, and then identify if it really is a big performance hit to do it a simple way (like storing floats in an stl stack, and converting when necessary)

(EDIT: Toolmaker's idea is valid, this is speed of access at expense of time to insert and space)

Share this post


Link to post
Share on other sites

class StackData
{
public:
virtual float operator()()=0;
virtual int operator()()=0;
virtual StackData& operator=(float f)=0;
virtual StackData& operator=(int i)=0;
};

template <typename T>
class StackDataT : public StackData
{
public:
float operator()() { return (float)_t; }
int operator()() { return (int)_t; }
StackData& operator=(float f) { _t = (T)f; return this; }
StackData& operator=(int i) { _t = (T)i; return this; }
private:
T _t;
};

// or you could use

class StackData
{
public:
float operator()() { if(_asFloat) return _d.f; else return (float)_d.i; }
int operator()() { if(_asFloat) return (int)_d.f; else return _d.i; }
StackData& operator=(float f) { _d.f = f; _asFloat = true; return this; }
StackData& operator=(int i) { _d.i = i; _asFloat = false; return this; }
private:
bool _asFloat;
union
{
float f;
int i;
} _d;
};





and now just use StackData instead of the float you normaly would use.

Hope this helps.

Share this post


Link to post
Share on other sites
Thanks, out of the ideas I've made something, but not with an union, with both int and float stored at the same time:


class IntFloat
{
private:
int i;
float f;
bool iu; //int up to date
bool fu; //float up to date

public:
void seti(int i)
{
this->i = i;
iu = 1;
fu = 0;
}
void setf(float f)
{
this->f = f;
iu = 0;
fu = 1;
}
int geti()
{
if(iu == 0) {i = int(f); iu = 1;}
return i;
}
float getf()
{
if(fu == 0) {f = float(i); fu = 1;}
return f;
}
};

Share this post


Link to post
Share on other sites
Hi,

your int(f) should be (int)f;
that looks like it's fast.
you could even overload the operators:


class IntFloat
{
//...
IntFloat& operator=(float f) { setf( f ); return this; }
IntFloat& operator=(int i) { seti( i ); return this; }
};

IntFloat var;

var = 1;
var = 3.0f;

Share this post


Link to post
Share on other sites
Quote:
Original post by dragongame
Hi,
your int(f) should be (int)f;


Actually, it's fine the way it is. C++ supports two different styles of casting, and I'm surprised you haven't seen this method before.

Share this post


Link to post
Share on other sites
Nope, each one does the exact same thing by saying you want to cast to an int. Use whichever you prefer.

Share this post


Link to post
Share on other sites
Okay,

i only knew the C cast style (int)bla and the C++ cast style static_cast<>() and the like.
okay ... int(bla) is much cleaner looking, I just have never seen it.
Every day you lern some thing.

Share this post


Link to post
Share on other sites
Sign in to follow this  

  • Advertisement
×

Important Information

By using GameDev.net, you agree to our community Guidelines, Terms of Use, and Privacy Policy.

We are the game development community.

Whether you are an indie, hobbyist, AAA developer, or just trying to learn, GameDev.net is the place for you to learn, share, and connect with the games industry. Learn more About Us or sign up!

Sign me up!