704.二分查找
题目:给定一个
n
个元素有序的(升序)整型数组nums
和一个目标值target
,写一个函数搜索nums
中的target
,如果目标值存在返回下标,否则返回-1
。
思路:
二分法的适用范围是有序且不重复。每次用数组中间的值middle与目标值target作比较,会出现两种情况[middle]>target
[middle]<target
二分法的第一种写法:
左闭右闭[left,right]
while(lift<=right)
{
middle = (lift+right)/2;
if(nums[middle]>target)
{
right = middle - 1;
}
else if(nums[middle]<target)
{
lift = middle + 1;
}
else
{
return middle;
}
}
第二种写法左闭右开[lift,right)
while(lift<right)
{
middle = (lift+right)/2;
if(nums[middle]>target)
{
right = middle;
}
else if(nums[middle]<target)
{
lift = middle + 1;
}
else
{
return middle;
}
}
完整左闭右闭二分法代码
#include <stdio.h>
int DoubleDichotomy(int n,int target);
int main()
{
int n,target,result;
printf("输入n和target");
scanf("%d%d",&n,&target);
result = DoubleDichotomy(n,target);
if(result == -1)
{
printf("查找失败");
}
else
{
printf("查找的下标为%d",result);
}
return 0;
}
/***************************************************************
** 功能: 左闭右闭二分法
** 参数: n:要输入的数组个数 target:目标值
** 返回值: 查找失败:-1 查找成功:middle
****************************************************************/
int DoubleDichotomy(int n,int target)
{
int nums[10000];
int lift,right,middle;
printf("输入数组值:");
for(int i = 0;i < n;i++)
{
scanf("%d",&nums[i]);
}
lift = 0;
right = n - 1;
while(lift<=right)
{
middle = (lift+right)/2;
if(nums[middle]>target)
{
right = middle - 1;
}
else if(nums[middle]<target)
{
lift = middle + 1;
}
else
{
return middle;
}
}
return -1;
}
完整左闭右开二分法代码
#include <stdio.h>
int DoubleDichotomy(int n,int target);
int main()
{
int n,target,result;
printf("输入n和target");
scanf("%d%d",&n,&target);
result = DoubleDichotomy(n,target);
if(result == -1)
{
printf("查找失败");
}
else
{
printf("查找的下标为%d",result);
}
return 0;
}
/***************************************************************
** 功能: 左闭右开二分法
** 参数: n:要输入的数组个数 target:目标值
** 返回值: 查找失败:-1 查找成功:middle
****************************************************************/
int DoubleDichotomy(int n,int target)
{
int nums[10000];
int lift,right,middle;
printf("输入数组值:");
for(int i = 0;i < n;i++)
{
scanf("%d",&nums[i]);
}
lift = 0;
right = n;
while(lift<right)
{
middle = (lift+right)/2;
if(nums[middle]>target)
{
right = middle;
}
else if(nums[middle]<target)
{
lift = middle + 1;
}
else
{
return middle;
}
}
return -1;
}
27. 移除元素
给你一个数组
nums
和一个值val
,你需要 原地 移除所有数值等于val
的元素,并返回移除后数组的新长度。不要使用额外的数组空间,你必须仅使用
O(1)
额外空间并 原地 修改输入数组。元素的顺序可以改变。你不需要考虑数组中超出新长度后面的元素。
思路
快慢指针操作,可以先看成两个数组,进行分析
完整代码
#include <stdio.h>
int removeElement(int* nums, int numsSize, int val);
int main()
{
int arr[10000],lenth,val;
printf("输入数组长度:");
scanf("%d",&lenth);
printf("输入要删除的元素:");
scanf("%d",&val);
printf("输入数组各元素:");
for(int i = 0;i < lenth;i++)
{
scanf("%d",&arr[i]);
}
printf("删除后的数组长度为:%d",removeElement(arr,lenth,val));
return 0;
}
/***************************************************************
** 功能: 数组删除元素
** 参数: nums:传入数组首地址 numsSize:数组大小 val:要删除的元素
** 返回值: slow:返回删除后的数组长度
****************************************************************/
int removeElement(int* nums, int numsSize, int val) {
int slow = 0;
for(int front = 0;front<numsSize;front++)
{
if(nums[front]!=val)
{
nums[slow] = nums[front];
slow++;
}
}
return slow;
}