Advertisement

Is there a way to swap two variables w/o a temp variable?

Started by July 27, 2000 05:45 PM
15 comments, last by Theses 24 years, 4 months ago
nt
Don''t like temp variables?

If you really hate temps that much, you could do this:

    void swap(int& a, int& b){  a = a ^ b;  b = a ^ b;  a = a ^ b;}    


The ^ is the exclusive-or (xor) operator. This will work, but it''s prone to developer-error, is unclear, and may not work as efficiently as using a temp, depending on compiler and architecture.


---- --- -- -
Blue programmer needs food badly. Blue programmer is about to die!
Advertisement
For the Win32-centric:

void swap(int &a, int &b)
{
b = InterlockedExchange(&a, b);
}

Plus, thread safety is yours at no extra cost!

Mason McCuskey
Spin Studios - home of Quaternion, 2000 GDC Indie Games Fest Finalist!
www.spin-studios.com
Founder, Cuttlefish Industries
The Cuttlefish Engine lets anyone develop great games for iPad, iPhone, Android, WP7, the web, and more!
As long as the architecture you''re writing for has a "real" xor machine code, it''s exactly as fast as the use of a temp, however it''s more memory efficient. I''d prefer this method when stack space is of concern, e.g. for use in a heavily recursive function.
As soon as your architecture is a theoretical one that uses a very limited - but complete - set of boolean operations, this might be incredibly slow since the compiler had to "build" the XOR call by some other operations thus becoming slower than a direct register-to-register copy.
Then again, when you''re using the function to actually swap complex data structures like strings or arrays via deep copy (i.e. not just swapping the references), the XOR method might be faster.
If you''re actually going to try it, tell us some results...

---
ls -lR|rm -rf /
(Best compression everywhere. Kids, don''t try this as root.)
Here:

void swap(int a, int b){    


------------------------------
#pragma twice
Here:

void swap(int a, int b){    __asm    {         push a         mov a, b         pop b    }} 

Or you could mov it to a register I think, because registers are pushed to the stack at the beginning of an __asm block aren''t they?


------------------------------
#pragma twice
Advertisement
Or you can use the exchange instruction ([xchg op1, op2] if I''m right)

Sludge Software
www.sludgesoft.com
Developing a secret of mana style role-playing-game
Sludge Softwarewww.sludgesoft.comDeveloping a secret of mana style role-playing-game

"For the Win32-centric:

void swap(int &a, int &b)
{
b = InterlockedExchange(&a, b);
}

Plus, thread safety is yours at no extra cost! "

Hi,

i fear that is very expensive because windows must acquire a mutex and after the operation release it again. Since mutexes are kernel objects that should be very expensive.
But if you know some better, please let me know because i like eccentric ideas like your''s a lot.

cu

Peter
HPH
No, InterlockedExchange doesn''t acquire a mutex. According to "Programming Applications for Microsoft Windows"(formerly "Advanced Windows"), the Interlocked family of instructions on the x86 use the lock prefix to guarantee that the calling CPU is the only CPU to modify the memory. Also, since x86 has very complex CISC instructions, most of which are guaranteed to be atomic (no interruption) you can easily implement these instructions with very little user-mode code. These functions will usually execute in less than 50 CPU cycles, and there is no kernel-mode transition. If you port your code to another Win32 platform, such as Alpha, these operations will probably be more expensive (but still not as expensive as acquiring and releasing a mutex.)
If you want to use ASM don''t forget the pentium processor has
a duel pipeline and cleverly perform two opertions at
once but there are a number of exceptions so possibly get away
with two clock clcyles instead of three!

Don''t use the exhange operator takes lots of CPU time for a single instruction!

useing the xor method that is cool

void _inline swap(unsigned long &a, unsigned long &b)
{

}

This topic is closed to new replies.

Advertisement