C++ int to byte array
Solution 1
Using std::vector<unsigned char>
:
#include <vector>
using namespace std;
vector<unsigned char> intToBytes(int paramInt)
{
vector<unsigned char> arrayOfByte(4);
for (int i = 0; i < 4; i++)
arrayOfByte[3 - i] = (paramInt >> (i * 8));
return arrayOfByte;
}
Solution 2
You don't need a whole function for this; a simple cast will suffice:
int x;
static_cast<char*>(static_cast<void*>(&x));
Any object in C++ can be reinterpreted as an array of bytes. If you want to actually make a copy of the bytes into a separate array, you can use std::copy
:
int x;
char bytes[sizeof x];
std::copy(static_cast<const char*>(static_cast<const void*>(&x)),
static_cast<const char*>(static_cast<const void*>(&x)) + sizeof x,
bytes);
Neither of these methods takes byte ordering into account, but since you can reinterpret the int
as an array of bytes, it is trivial to perform any necessary modifications yourself.
Solution 3
You can get individual bytes with anding and shifting operations:
byte1 = nint & 0x000000ff
byte2 = (nint & 0x0000ff00) >> 8
byte3 = (nint & 0x00ff0000) >> 16
byte4 = (nint & 0xff000000) >> 24
Solution 4
Another useful way of doing it that I use is unions:
union byteint
{
byte b[sizeof int];
int i;
};
byteint bi;
bi.i = 1337;
for(int i = 0; i<4;i++)
destination[i] = bi.b[i];
This will make it so that the byte array and the integer will "overlap"( share the same memory ). this can be done with all kinds of types, as long as the byte array is the same size as the type( else one of the fields will not be influenced by the other ). And having them as one object is also just convenient when you have to switch between integer manipulation and byte manipulation/copying.
Solution 5
An int (or any other data type for that matter) is already stored as bytes in memory. So why not just copy the memory directly?
memcpy(arrayOfByte, &x, sizeof x);
A simple elegant one liner that will also work with any other data type.
If you need the bytes reversed you can use std::reverse
memcpy(arrayOfByte, &x, sizeof x);
std::reverse(arrayOfByte, arrayOfByte + sizeof x);
or better yet, just copy the bytes in reverse to begin with
BYTE* p = (BYTE*) &x;
std::reverse_copy(p, p + sizeof x, arrayOfByte);
If you don't want to make a copy of the data at all, and just have its byte representation
BYTE* bytes = (BYTE*) &x;
justme_
Updated on August 23, 2020Comments
-
justme_ over 3 years
I have this method in my java code which returns byte array for given int:
private static byte[] intToBytes(int paramInt) { byte[] arrayOfByte = new byte[4]; ByteBuffer localByteBuffer = ByteBuffer.allocate(4); localByteBuffer.putInt(paramInt); for (int i = 0; i < 4; i++) arrayOfByte[(3 - i)] = localByteBuffer.array()[i]; return arrayOfByte; }
Can someone give me tip how can i convert that method to C++?
-
James Kanze about 13 yearsMaybe. Not on an Intel box (or at least it won't give the same results).
-
Sxl about 13 yearsI'm curious: why did you do two
static_cast<>
s instead of onereinterpret_cast<>
? -
BlackBear about 13 yearshe asked exactly the opposite :)
-
jberg about 13 yearswow, I fail! Always feel like if I don't reply right away a million other people will. I was right, but I suppose I should make sure to get the question right hahaha
-
James McNellis about 13 yearsTo elaborate: There was lengthy discussion here a year or two ago about whether a
reinterpret_cast
was guaranteed to be equivalent to the pair ofstatic_cast
. If I recall correctly it was basically agreed that both should always work, but it was all very convoluted so I still avoidreinterpret_cast
. -
BlackBear about 13 yearsyeah, me too try to answer as fast as possible, and sometimes write such a bullsh*ts ;)
-
James Kanze about 13 yearsThe Java code generates a big endian representation; you generate a littel endian one. (I'd also just use the shift count as the loop control:
int i = 32; while ( i != 0 ) { arrayOfByte[i] = paramInt >> i; i -= 8; }
-
Tomáš Zato about 11 years@JamesKanze: wait... can you really use
i
to accessarrayOfByte
when it will have values of[32, 24, 16, 8]
? I think you should doarrayOfByte[i/8]
. -
James Kanze about 11 years@TomášZato Yes; The index should be
i/8
. -
Jason Rice about 8 yearsIt's still useful.
-
MateuszL over 5 yearsReading from wrong union member is Undefined Behavior and misuse of union
-
Lightness Races in Orbit over 5 yearsThis is wrong. This is not what unions are for. This is not how unions work. Myth!
-
Yan almost 5 yearsThe result of this method seems to depend on the endianness. Assume x=0x4142, run this process on a little endian machine, iterate the bytes array and print each byte, you'll get "BA". If you want to get "AB", you have to reverse the result by yourself.
-
RoboticForest over 4 yearsOn some machines this is very clever, but sadly it's not standard and is dangerous. See this union reference. "The union is only as big as necessary to hold its largest data member. The other data members are allocated in the same bytes as part of that largest member. The details of that allocation are implementation-defined, and it's undefined behavior to read from the member of the union that wasn't most recently written. Many compilers implement, as a non-standard language extension, the ability to read inactive members of a union."
-
Ayxan Haqverdili almost 4 yearsIs it well defined to cast an int to a byte array? I thought accessing an object as if it were some other type is undefined behavior.