Given a sorted array of integers, find the starting and ending position of a given target value.

Your algorithm's runtime complexity must be in the order of O(log n).

If the target is not found in the array, return [-, -].

For example,
Given [, , , , , ] and target value ,
return [, ].

Analysis: 这道题是二分查找Search Insert Position的变体,思路并不复杂,就是先用二分查找找到其中一个target,然后再往左右找到target的边缘。找边缘的方法跟二分查找仍然是一样的,只是相等的情况依然要往左找(找左边缘)或往右找(找右边缘)。这样下来总共进行了三次二分查找,所以算法的时间复杂度仍是O(logn),空间复杂度是O(1)。

Notice: 对停止的边界条件极不熟悉,需要总结,参见Binary Search的Summary

本题的精髓和难点在于寻找左右边沿,方法是Binary Search的变体,只不过这次是要左右相遇。以找左边缘为例,while循环里要么A[m] < target, l 跳到m+1, 要么A[m]==target, r 跳到m-1, 直到l > r为止,这时候l所在的位置就是要求的左边缘。而如果是找右边缘,l > r之后,r所在位置就是要求的右边缘。l和r所停的位置正好是目标数的后面和前面。

找左边沿可以认为是在找一个比target略小的目标数(因为等于target的时候移动的是右边缘),这个目标数在A中不存在,所以当循环结束时候,l, r分别处在目标数的后面和前面。如果我们找的是左边缘,那么这个左边缘应该是在目标数右边,所以就是l所处的位置

整体如果想用iterative的方法来写:

两次binary search, 一次找左边缘,一次找右边缘, be carefule of line 12, r有可能<0

 public class Solution {
public int[] searchRange(int[] nums, int target) {
int[] res = new int[]{-1, -1};
if (nums==null || nums.length==0) return res;
int l=0, r=nums.length-1;
int m = l + (r-l)/2;
while (l <= r) { // find right edge
m = l + (r-l)/2;
if (nums[m] <= target) l = m + 1;
else r = m - 1;
}
if (r<0 || nums[r] != target) return res;
else res[1] = r; l = 0;
//no need to set r = nums.length - 1, because r is already at right place
while (l <= r) {
m = l + (r-l)/2;
if (nums[m] < target) l = m + 1;
else r = m - 1;
}
res[0] = l;
return res;
}
}

最新文章

  1. Redis教程(十五):C语言连接操作代码实例
  2. EF LEFT JON 关联查找
  3. 数据视化Echarts+百度地图API实现市县区级下钻
  4. Oracle存储过程procedure
  5. nginx对于Yii2的前后台的配置
  6. axure篇
  7. PB数据库相关
  8. ORDER BY RAND()
  9. STM32F103RC进入串口3接收中断产生HardFault_Hander问题解决!
  10. DOM 遍历-同胞
  11. Nginx 静态资源缓存设置
  12. RabbitMQ指南之一:&quot;Hello World!&quot;
  13. hdu 4542 &quot;小明系列故事——未知剩余系&quot; (反素数+DFS剪枝)
  14. 在userMapper.xml文件中模糊查询的常用的3种方法
  15. [视频]K8飞刀 Google黑客功能教程
  16. SQL Server 2008 management studio 无法连接到(local)解决方法
  17. 新装的MySQL没有密码怎么办
  18. 第 3 章 镜像 - 013 - Dockerfile 构建镜像
  19. vim插件之pathogen,NERDTree,Command-T,Powerline
  20. MVC知识记录

热门文章

  1. java 从上至下打印二叉树
  2. Write-Off
  3. 模拟webpack 实现自己的打包工具
  4. ARP详解
  5. MLP多层感知机
  6. Python Django 版本对应表
  7. CSP模拟赛 number (二分+数位DP)
  8. 58、springmvc-定制与接管SpringMVC
  9. 53、servlet3.0-简介&amp;测试
  10. c# 关于mongo bson转json的问题