Quote:Original post by Hodgman
Off the top of my head, I think it's something like return -(~x);...
How about return (int)( (unsigned int)(~x) ); ??
although I'm not sure...
Quote:Original post by Hodgman
Off the top of my head, I think it's something like return -(~x);...
Quote:Original post by jorelmbNot quite. However this does work:
How about return (int)( (unsigned int)(~x) ); ??
although I'm not sure...
unsigned plus(unsigned n) { return abs(~n);}
For positive integers on two's complement machines anyway, though negative ones can be handled as well with a bit of branching. Admittedly using the standard library might be viewed as cheating.unsigned plus(unsigned n) { return sizeof(struct { char padding, array[n]; });}
Assuming the compiler doesn't decide to include any structure padding of course, I honestly don't know what the standard allows in this case. At least it compiles and runs without warnings in GCC's pedantic mode.static int AddAwesome(int x, char p[]){ return (int)&x[&p[1]];}int AddOne(int x){ return AddAwesome(x, 0);}
Quote:Original post by hh10k
*** Source Snippet Removed ***
Quote:Usually, the value represented by postfix-expression is a pointer value, such as an array identifier, and expression is an integral value (including enumerated types). However, all that is required syntactically is that one of the expressions be of pointer type and the other be of integral type. Thus the integral value could be in the postfix-expression position and the pointer value could be in the brackets in the expression or subscript position.
int Add(int x, int y){ char *p = 0; return (int)&x[&p[y]];}int main(){ int eight = Add(5, 3); return 0;}
Quote:Original post by jhq
And I think the context of this question is to improve the efficiency, not only bit manipulation
Quote:Original post by hh10k
*** Source Snippet Removed ***
C time: 475 mspinacolada time: 630 msZahlman time: 473 mshh10k time: 472 msDevFred time: 941 ms
#include stuff.. int addOnepinacolada(int i){ __asm { mov eax, i; add eax, 1; mov i, eax; }}int addOneDevFred(int i){ __asm { inc i; } return i;}int addOneC(int i){ return i + 1;}int increment(int x) { return (x & 1) ? (increment(x >> 1) << 1) : (x | 1);}static int AddAwesome(int x, char p[]){ return (int)&x[&p[1]];}int addOnehh10k(int x){ return AddAwesome(x, 0);}int _tmain(int argc, _TCHAR* argv[]){ timeBeginPeriod(1); int ta, tb; __int64 counts = 500000000; ta = timeGetTime(); for(__int64 i = 0; i < counts; i++) int q = addOneC(1234); tb = timeGetTime(); cout << "C time: " << tb - ta << " ms\n"; ta = timeGetTime(); for(__int64 i = 0; i < counts; i++) int q = addOnepinacolada(1234); tb = timeGetTime(); cout << "pinacolada time: " << tb - ta << " ms\n"; ta = timeGetTime(); for(__int64 i = 0; i < counts; i++) int q = increment(1234); tb = timeGetTime(); cout << "Zahlman time: " << tb - ta << " ms\n"; ta = timeGetTime(); for(__int64 i = 0; i < counts; i++) int q = addOnehh10k(1234); tb = timeGetTime(); cout << "hh10k time: " << tb - ta << " ms\n"; ta = timeGetTime(); for(__int64 i = 0; i < counts; i++) int q = addOneDevFred(1234); tb = timeGetTime(); cout << "DevFred time: " << tb - ta << " ms\n"; cin.ignore(1); timeEndPeriod(1); return 0;}
Quote:Original post by Jesper T
Quite surprising that the asm was so much slower though.
Quote:Original post by Jesper T
Tested some of the versions
Result:C time: 475 mspinacolada time: 630 msZahlman time: 473 mshh10k time: 472 msDevFred time: 941 ms
The times fluctuate with up to 5 ms each time I run the test. Quite surprising that the asm was so much slower though.
for(__int64 i = 0; i < counts; i++) int q = addOneC(1234);
int q = 0;for(__int64 i = 0; i < counts; i++) q += addOneC(1234);std::cout << q;
Quote:And I think the context of this question is to improve the efficiency, not only bit manipulation