Question

Right now I have this code:

uint64_t buffer = 0;
const uint8_t * data = reinterpret_cast<uint8_t*>(&buffer);

And this works, but it seems risky due to the hanging pointer (and looks ugly too). I don't want naked pointers sitting around. I want to do something like this:

uint64_t buffer = 0;
const std::array<uint8_t, 8> data = partition_me_softly(buffer);

Is there and c++11 style construct that allows for me to get this into a safe container, preferable a std::array out of an unsigned int like this without inducing overhead?

If not, what would be the ideal way to improve this code to be more safe?


So I modified dauphic's answer to be a little more generic:

template <typename T, typename U>
std::array<T, sizeof(U) / sizeof(T)> ScalarToByteArray(const U v)
{
    static_assert(std::is_integral<T>::value && std::is_integral<U>::value, 
        "Template parameter must be a scalar type");
    std::array<T, sizeof(U) / sizeof(T)> ret;
    std::copy((T*)&v, ((T*)&v) + sizeof(U), ret.begin());
    return ret;
}

This way you can use it with more types like so:

uint64_t buffer = 0;
ScalarToByteArray<uint8_t>(buffer);
Was it helpful?

Solution

If you want to store an integer in a byte array, the best approach is probably to just cast the integer to a uint8_t* and copy it into an std::array. You're going to have to use raw pointers at some point, so your best option is to encapsulate the operation into a function.

template<typename T>
std::array<uint8_t, sizeof(T)> ScalarToByteArray(const T value)
{
    static_assert(std::is_integral<T>::value, 
        "Template parameter must be a scalar type");
    std::array<uint8_t, sizeof(T)> result;
    std::copy((uint8_t*)&value, ((uint8_t*)&value) + sizeof(T), result.begin());
    return result;
}
Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top