计算两个数的和,我们首先肯定想到的是加法运算,但今天我们通过C语言的其他语法来求两个数的和。
今天我介绍两种方法:
方法一:用位运算求两数的和
我们设两个数x=666,y=888;我们需要设计函数来求两数和sum=1554。
我们通常是将两个数从低位开始相加,然后考虑是否有进位。但位运算不能将上述步骤一步完成。
所以我们今天将“加”、“进位”这两步分开实现,然后最后相加计算即可。
1、我们可以通过位运算^(异或)来计算两个数只相加 ,而不考虑进位,即666+888=444。
2、我们可以通过位运算&(按位与)来计算两个数的进位,即666+888=111。
但还需<<(左移)一位,因为最后一位没有进位,所以最后得到进位的结果为1110。
3、将进位的数值和相加的数字进行相加运算即为最终结果,由于不能用+运算符,所以此处我们可以用递归或循环实现。
代码实现:
//递归、位运算实现
int ADD(int x,int y)
{
if (y == 0)
return x;
int sum = x^y; //各位相加(不带进位)
int carry = (x & y) << 1; //只存两个数相加的进位
//将进位与不带进位求和(由于不能用加法,所以递归,到carry为0时返回)
return ADD(sum, carry);
}
//位运算非递归版
int ADD2(int x, int y)
{
int sum = 0;
int carry = 0;
while (y != 0)
{
sum = x^y;
carry = (x & y) << 1;
x = sum;
y = carry;
}
//当循环至y=0时,即进位为0,两数之和已经加至x上,所以返回x即可
return x;
}
方法二:通过指针的性质来求两个数的和
我们都知道指针其实就是地址,指针的偏移量其实可以看做是加法运算,我们通过指针的偏移量来完成两个数相加。
首先我们将x+y中的x强转为char*型的地址用一个指针变量保存,然后通过对该指针进行偏移量为y的偏移,再取偏移后的地址强转为int型即可。
代码实现:
//通过指针的偏移量的特性实现
int ADD3(int x, int y)
{
//由于指针可以看成地址,所以可以将x转为地址形式通过指针的便宜来加上y
char *z = (char*)x;
return (int)&z[y]; //z + sizeof(char)*y 等价于 x+y
}
总结:
以上方法均可以实现不用算术运算符来实现两个数相加,主要用的是C语言语法的一些特性。通过这样的练习我们可以对用到的语法有更深层次的理解,在以后的学习中我们要善于思考、善于发现这些语法的特性,才能在思维上得到提高。