Original Post
Hello, i 'd like to share a performance observation i made about the following code: when i use the default assignment operator of the Test struct, the execution time is around 6600 milliseconds, but when i overload the assignment operator use memcpy with the size of the block to copy being known at compile time, the same program executes at around 3800 milliseconds. I get the same speed improvement if i replace this: with this: I 'm using g++ 4.1.2 with the -O6 option. The default assignment probably does 4 * 1 byte copies instead of doing 1 * 32-bit like memcpy probably does. But this optimization is done if i use the default assignment operator and just enclose the data member declarations in a union{struct{ }} block. I haven't tested this on visual studio because it ' s currently not installed on my pc. I would just like to read some comments on this, for example is my test invalid for some reason, does this happen in MSVC too? If i replace one or two members with 16-bit ints, the speed gain is much smaller, but it exists, and maybe in some cases it would be needed.
#include <iostream>
#define UInt8 unsigned char
#define UInt16 unsigned short
#define UInt32 unsigned int
#define UInt64 unsigned long long
inline UInt64 CPUClock()
{
UInt32 lo, hi;
__asm__ __volatile__ ("rdtsc" : "=a" (lo), "=d" (hi));
return (UInt64)hi << 32 | lo;
};
struct Test
{
UInt8 byte0;
UInt8 byte1;
UInt8 byte2;
UInt8 byte3;
Test(){};
Test(UInt8 a_byte0, UInt8 a_byte1, UInt8 a_byte2, UInt8 a_byte3):
byte0(a_byte0), byte1(a_byte1), byte2(a_byte2), byte3(a_byte3){};
/*inline Test &operator=(Test &a_test)
{
memcpy((void*)this, (void*)(&a_test), sizeof(Test));
return *this;
};*/
};
#define N 2048576
int main()
{
int size = sizeof(Test);
Test *src = new Test[N];
Test *dst = new Test[N];
UInt64 start;
UInt64 end;
start = CPUClock();
for(int i = 0; i < 1000; i++)
{
for(int j = 0; j < N; j++)
{
dst[j] = src[j];
};
};
end = CPUClock();
std::cout << "Time:\t" << ((float)(end - start)) / 3010500.0 << std::endl;
return 0;
};
UInt8 byte0;
UInt8 byte1;
UInt8 byte2;
UInt8 byte3;
union
{
struct
{
UInt8 byte0;
UInt8 byte1;
UInt8 byte2;
UInt8 byte3;
};
};