您的位置:首页 > 职场人生

不借助第三个变量交换两个整数

2016-08-06 21:40 253 查看
假设两个数x和y,则有:

方法1,算术运算(加减):

方法2,逻辑运算(异或):

关于异或运算要牢记两个原则:

任何一位二进制数同 1 异或都会变成另外一个(0 同 1 异或的结果是 1,1 同 1 异或的结果是 0)

任何一位二进制数同 0 异或都保持不变(0 同 0 异或的结果是 0,1 同 0 异或的结果是 1)

实现这个操作的方法很多。

最基本的方法就是使用一个临时变量,具体的代码如下:

int a,b;
int tmp;

tmp=a;

a=b;

b=tmp;
另外,还经常出现的一种情况是不使用临时变量来交换两个整型数,一般常见的方法有两种:加法和异或运算,具体如下表所示:

void swap1(int& x,int& y)

{

x=x+y;

y=x-y;

x=x-y;

}

void swap2(int &x,int &y)

{

x=x-y;

y=x+y;

x=y-x;

}

void swap3(int& x,int& y)

{

x ^= y;

y ^= x;

x ^= y;

}

x和y同号的情况下容易溢出
x和y异号的情况下容易溢出
 
左边的两种交换也存在问题就是整数的溢出。

所以更严谨的做法如下:
void swap4(int &x,int &y)

{
if(x==y)
return ;
if((x>0&&y>0)||(x<0&&y<0)) {

x=x-y;

y=x+y;

x=y-x;

}
else{

x=x+y;

y=x-y;

x=x-y;

}

}

void swap5(int &x,int &y)

{
if(x==y)
return;

x^=y;

y^=x;

x^=y;

}

void swap7(int &x,int &y)

{
if(x==y)
return;

y=x+y-(x=y);

}

【扩展】

另外,还有不使用临时变量交换N个整型数的操作, 

有N(N>=2)个变量,不使用临时变量,如何顺次交换它们的值?能否只用一条语句实现?如
+---+---+---+---+---+

| a | b | c | d | e |

+---+---+---+---+---+

| 1 | 2 | 3 | 4 | 5 |

+---+---+---+---+---+
 
要把它变为
+---+---+---+---+---+

| a | b | c | d | e |

+---+---+---+---+---+

| 2 | 3 | 4 | 5 | 1 |

+---+---+---+---+---+
怎样实现?

首先,我们考虑用异或实现两个变量的交换,可参考我的这篇文章《不用临时变量交换两个数的值》。用C++写函数如下:

 
int &swap(int &a, int &b)
{

    b = b ^ a;

    a = a ^ b;

    b = b ^ a;

    return b;
}

然后可以把代码优化为:
int &swap(int &a, int &b)
{

    b ^= a;

    a ^= b;

    b ^= a;

    return b;
}

继续优化,把三句压缩为一句,如下:
int &swap(int &a, int &b)
{

    b ^= a ^= b ^= a;

    

    return b;
}

还可再优化,如下:
int &swap(int &a, int &b)
{

    return (b ^= a ^= b ^= a);
}

现在来顺次交换5个变量的值,如下:
swap(a, b);        //返回b

swap(b, c);        //返回c

swap(c, d);        //返回d

swap(d, e);        

既然有返回值,那么可以写成链式的,如下:
swap(a, b);                                 //返回b

swap(swap(a, b), c);                        //返回c

swap(swap(swap(a, b), c), d);               //返回d

swap(swap(swap(swap(a, b), c), d), e);        

现在,让我们来把swap函数依次用相应的函数体替换掉,如下:
e ^= d ^= e ^= swap(swap(swap(a, b), c), d);

e ^= d ^= e ^= d ^= c ^= d ^= swap(swap(a, b), c);

e ^= d ^= e ^= d ^= c ^= d ^= c
^= b ^= c ^= swap(a, b);

e ^= d ^= e ^= d ^= c ^= d ^= c
^= b ^= c ^= b ^= a ^= b ^= a;

内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签:  面试题 算法