• 10
• 9
• 12
• 14
• 15

# How do you deal with tons of different same fundamental data types?

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

## Recommended Posts

Let us stay simple and state I want and need to use a single definition for fundamental types with fixed dimensions. (let's forget about why do Microsoft and the C/C++ standards provides non-fixed size...)

How do you deal with the tons of the Windows data types, the VC compiler data types, and the C/C++ unfixed data types? Do you split into two parts your project, one where you code only with your own defined types (where you do not have any external library includes) and another where you have to deal with the Windows headers or other libraries?

Actually I pretty like to use the cstding fixed-size integers, but every-time a function or a structure except a Windows data type I always check for compatibility through C++-style casts (not C-style casts). It is useless to state how boring and annoying is this.

I was thinking to create an header where using tons of static_assert and check the compatibility of my types with Windows Data types and C/C++ types. But I am not sure about that, since I was to add it in the PCH after the Windows and the C/C++ standard library includes.

So, any advice how to make neat all this is accepted.

Edited by Alessio1989

##### Share on other sites

I include <cstdints>, and use the standardized fixed width types: uint64_t, uint32_t, uint16_t, uint8_t, etc...

If your implementation doesn't support that type, then that type won't be defined, afaik.

Typically, I use int or unsigned for general usage, and size_t, uint32_t, etc... to more explicitly indicate my assumptions only when I need the fixed width.

Occasionally I have to talk to other 3rd party libraries that use other formats, and in those situations I try to isolate the additional formats only to the borders of where my code needs to talk to that library.

##### Share on other sites

What do you do in a piece of code where you retrieve/pass parameters to/from Windows libraries? Actually I pass my types (or just <cstint> types) and then I static_cast them from/to windows data types. But this is really annoying.

Edited by Alessio1989

##### Share on other sites

I don't deal with Win32 directly, but I do deal with some other third-party libraries with their own types (Qt, GL, and SFML for example).

In those cases, if it makes sense to do so, I do static_cast. That's the appropriate way to convert between two similar data types.

Yea, it can get slightly annoying, but in classes that deal excessively with a third-party library, sometimes it makes more sense to treat that class as an extension to that third-party library, and use that library's third-party types internally or even externally.

Every class basically falls into "My code" or "Extension of that library's code", so either my code only calls into that library in a few isolated places, or it calls into my class that wraps functionality and uses the types internally.

##### Share on other sites
Keeping 'their' code separate at the edges of 'your' code is also helpful in switching to some other library, if you ever need to do that.

##### Share on other sites

Windows-specific code should always be strongly decoupled/isolated from the rest of your code-base. That's just good cross-platform practice!

Only very small amounts of your game should interact with Windows (or other low-level APIs) directly, and these parts of your game should be isolated behind some nice, easy-to-use interface. The rest of your game (99% of your code) should be all nice and standard and clean and portable :)

##### Share on other sites

Yes, I still try to separate my own code with code that directly interact with 3rd party libraries (like win32 APIs). I was wondering if there are some dirty tricks (even preprocessor tricks) to feed my laziness and avoid explicit static_cast et similia.

Another question: is a good practice to "undef" 3rd party data types in the project parts you do not need them? I saw that in the UE source code.

Edited by Alessio1989

##### Share on other sites

Another question: is a good practice to "undef" 3rd party data types in the project parts you do not need them? I saw that in the UE source code.

Don't include them in the other parts in the first place! IMHO having to attempt to undef stuff is a failing.
I've worked with quite a few engines that put "windows.h" into the PCH, which pollutes every single damn file... IMHO this is a terrible thing to do.
Keep implementations hidden

I was wondering if there are some dirty tricks (even preprocessor tricks) to feed my laziness and avoid explicit static_cast et similia.

You can make some shorthands...
MyVec4 cast( const TheirVec4& v )
{
static_assert( sizeof(MyVec4) == sizeof(TheirVec4) );
static_assert( offsetof(MyVec4,x) == offsetof(TheirVec4,x) );
static_assert( offsetof(MyVec4,y) == offsetof(TheirVec4,y) );
static_assert( offsetof(MyVec4,z) == offsetof(TheirVec4,z) );
static_assert( offsetof(MyVec4,w) == offsetof(TheirVec4,w) );
return *(MyVec4*)&v;
}
^^ It's good practice to always document any assumption that you make with an assertion or compile-time assertion. Here I'm documenting that it's safe to reinterpret cast these two vec4 types

As for the windows types, many of them are just typedefs, so there's no casting requried, e.g.
BYTE windows = 42;
uint8_t portable = windows;//no cast, because BYTE is an unsigned 8bit integer!
Edited by Hodgman