1. 剑指 Offer 65. 不用加减乘除做加法
位运算实现加法运算
- 进位运算用按位与
&
和左位移位移运算<<
实现- 本位(非进位)运算用按位异或
^
实现- 考虑负数情况时将进位运算结果转换为
unsigned
型
// 剑指Offer65.不用加减乘除做加法
int Add(int num1, int num2) {
//进位运算结果为0时运算结束
while (num2)
{
//tmp存储进位运算结果
unsigned int tmp = (unsigned int) (num1 & num2) << 1;
//非进位运算结果
num1 = num1 ^ num2;
//进位运算结果赋给num2
num2 = tmp;
}
return num1;
}
2. 238. 除自身以外数组的乘积
左右累乘
常规做法
int* productExceptSelf(int* nums, int numsSize, int* returnSize){
int* ret=malloc(sizeof(int)*numsSize);
int* left=malloc(sizeof(int)*numsSize);
int* right=malloc(sizeof(int)*numsSize);
*returnSize=numsSize;
int l=1,r=1;
for(int i=0;i<numsSize;i++)
{
if(i==0)
{
left[i]=1;
}
else
{
l*=nums[i-1];
left[i]=l;
}
}
for(int j=numsSize-1;j>=0;j--)
{
if(j==numsSize-1)
{
right[j]=1;
}
else
{
r*=nums[j+1];
right[j]=r;
}
ret[j]=left[j]*right[j];
}
return ret;
}
空间复杂度O(1)
的做法
先在返回数组上生成左边乘积数组,再动态生成右边乘积,乘到对应的位置
int* productExceptSelf(int* nums, int numsSize, int* returnSize){
int* ret=malloc(sizeof(int)*numsSize);
ret[0]=1;
for(int i=1;i<numsSize;i++)
{
ret[i]=ret[i-1]*nums[i-1];
}
int r=1;
for(int i=numsSize-1;i>=0;i--)
{
ret[i]=ret[i]*r;
r*=nums[i];
}
*returnSize=numsSize;
return ret;
}
3. 728. 自除数
直接判断
/**
* Note: The returned array must be malloced, assume caller calls free().
*/
int decide(int num)
{
int self=num;
int k=0;
while(num)
{
int divider=num%10;
if(divider!=0 && self%divider == 0)
{
k=1;
}
else
{
return 0;
}
num/=10;
}
return k;
}
int* selfDividingNumbers(int left, int right, int* returnSize){
int count=0;
int i=0;
int* p=malloc(sizeof(int)*(right-left+1));
for(i=left;i<=right;i++)
{
if(decide(i)==1)
{
p[count++]=i;
//count++;
}
}
*returnSize=count;
return p;
}