在排序数组中查找元素的第一个和最后—个位置

#include <iostream>
#include <vector>

using namespace std;

int searchBeginPos(vector<int> srcVec, int target)
{
	//思路分析
	//先通过二分查找的方法找目标值,如果找不到目标值,直接返回-1,
	//如果能找到目标值,则要分析目标值是不是srcVec的左边界,即mid是不是0,
	
	//如果是边界,则mid就是目标值区间的最左边的位置
	
	//如果不是边界则看紧挨目标值左边的值是不是小于目标值,
	//如果是,则当前位置就是目标值区间的第一个位置
	//如果不是,则在目标值左边数据区间接着寻找目标值

	int left = 0;
	int right = srcVec.size() - 1;

	while (left <= right)
	{
		int mid = left + (right - left) / 2;

		if (srcVec[mid] == target)
		{
			//如果mid是边界,则mid就是目标值区间的最左边的位置
			if (mid == 0)
			{
				return mid;
			}
			//上面的if判断同时保证了srcVec[mid - 1]不会越界,但是如果去掉上面的条件
			//改为if (mid - 1 >= 0 && srcVec[mid - 1] < srcVec[mid])
			//则当mid == 0 的时候,没有返回正确的值,即当target的边界值为第一个值的时候
			if (srcVec[mid - 1] < srcVec[mid])
			{
				//当前mid所在的位置就是target所在区间的最左边的元素
				return mid;
			}
			//接着去右边找下一个target值
			right = mid - 1;
		}
		else if (srcVec[mid] < target)
		{
			left = mid + 1;
		}
		else
		{
			right = mid - 1;
		}
	}
	return -1;
}

int searchEndPos(vector<int> srcVec, int target)
{
	//思路分析
	//先通过二分查找的方法找目标值,如果找不到目标值,直接返回-1,
	//如果能找到目标值,则要分析目标值是不是srcVec的右边界,即mid是不是srcVec.size() - 1,

	//如果是边界,则mid就是目标值区间的最右边的位置

	//如果不是边界则看紧挨目标值右边的值是不是大于目标值,
	//如果是,则当前位置就是目标值区间的最后一个位置
	//如果不是,则在目标值右边数据区间接着寻找目标值

	int left = 0;
	int right = srcVec.size() - 1;

	while (left <= right)
	{
		int mid = left + (right - left) / 2;

		if (srcVec[mid] == target)
		{
			//如果mid是边界,则mid就是目标值区间的最左边的位置
			if (mid == srcVec.size() - 1)
			{
				return mid;
			}

			if (srcVec[mid + 1] > srcVec[mid])
			{
				//当前mid所在的位置就是target所在区间的最右边的元素
				return mid;
			}
			//接着去右边找下一个target值
			left = mid + 1;
		}
		else if (srcVec[mid] < target)
		{
			left = mid + 1;
		}
		else
		{
			right = mid - 1;
		}
	}
	return -1;
}

int main()
{
	vector<int> testVec = { 5, 7, 7, 8, 8, 10 };

	int target = 8;
	int begin = searchBeginPos(testVec, target);
	int end = searchEndPos(testVec, target);
	cout << target << "begin = " << begin << "end = " << end << endl;

	target = 7;
	begin = searchBeginPos(testVec, target);
	end = searchEndPos(testVec, target);
	cout << target << "begin = " << begin << "end = " << end << endl;

	target = 5;
	begin = searchBeginPos(testVec, target);
	end = searchEndPos(testVec, target);
	cout << target << "begin = " << begin << "end = " << end << endl;

	target = 10;
	begin = searchBeginPos(testVec, target);
	end = searchEndPos(testVec, target);
	cout << target << "begin = " << begin << "end = " << end << endl;

	target = 20;
	begin = searchBeginPos(testVec, target);
	end = searchEndPos(testVec, target);
	cout << target << "begin = " << begin << "end = " << end << endl;
}

 

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值