数字在排数组中的出现次数

补充:默认升序数组。

思路:

升序,就先想到二分法,找到第一个k的索引,最后一个k的索引,last-first+1

1、查第一个k

if[mid] > k:

说明第一个k出现在左边的子数组,因此 end = mid-1;

if [mid] < k:

说明第一个k出现在右边的数组,因此 start = mid+1;

if [mid] == k:

得看mid之前还有没有k了,如果有,说明k还在左边数组,如果没有了,说明这个[mid]就正好是第一个k;

看mid之前,得保证mid之前确实还有元素,比如说mid=0,那么mid之前就没有元素了,那么[mid]就是第一个k,即数组第一个元素就是k

2、查找最后一个k

同理,不再描述

 

测试:

数组中包含k,数组中没有k,查找的k只出现一次

边界情况:

k是数组最小值;

k是最大值;

数组只有一个数字。

代码

 1 class Solution {
 2 public:
 3     int GetNumberOfK(vector<int> data ,int k) {
 4         if(data.empty()) return 0;
 5         int num = 0;
 6         int first=getfirstk(data,0,data.size()-1,k);
 7         int last = getlastk(data,0,data.size()-1,k);
 8         if(first>-1 && last>-1) num=last-first+1;
 9         return num;
10     }
11     int getfirstk(vector<int> vec,int start,int end,int k){
12         if(start>end) return -1;//-1是因为如果第一个k在0索引的情况
13         int mid=start+(end-start)/2;//不用(start+end)/2是害怕start+end时内存溢出
14         int hehe = vec[mid];
15         if(hehe==k){
16             if((mid>start && vec[mid-1]!=k) || mid==start) return mid;
17             else end=mid-1;
18         }
19         else if(hehe>k) end=mid-1;
20         else start=mid+1;
21         return getfirstk(vec,start,end,k);
22     }
23     int getlastk(vector<int> vec,int start,int end,int k){
24         if(start>end) return -1;
25         int mid=start+(end-start)/2;
26         int hehe = vec[mid];
27         if(hehe==k){
28             if((mid<end && vec[mid+1]!=k) || mid==end) return mid;
29             else start = mid+1;
30         }
31         else if(hehe>k) end=mid-1;
32         else start=mid+1;
33         return getlastk(vec,start,end,k);
34     }
35 };

 

posted @ 2019-07-13 16:55  Austin_anheqiao  阅读(195)  评论(0编辑  收藏  举报