题目:数字在升序数组中出现的次数

描述:给定一个长度为 n 的非降序数组和一个非负数整数 k ,要求统计 k 在数组中出现的次数

要求:数据范围:0≤n≤1000,0≤k≤100,数组中每个元素的值满足0≤val≤100
要求:空间复杂度O(1),时间复杂度O(logn)

1.二分查找

二分查找是一种在有序数组中运用到的快速查找的算法,也称“折半查找(Binary Search)”。时间复杂度为O(logn),相对遍历查找,是一种较为优秀的算法。基本原理是通过将一个有序数组的中间值与目标值进行对比,若恰好等于中间值则返回该值;若目标值大于中间值,则压缩左边界,逼近目标值;若目标值小于中间值,则压缩右边界,逼近目标值。代码示例如下:(假设数组升序排列)

#include<stdio.h>
int find_t(int* a, int key, int sz)
{int left = 0, right = sz - 1;int mid = 0;while (left <=right)//循环条件是左边小于等于右边,当左边大于右边,不用再循环;{mid = (right - left) / 2 + left;//找到中间值(此做法是为了避免溢出)if (a[mid] < key)//当要找到的key在中间值的右边时{left = mid+1;//左边界向前进一位,压缩寻找范围}else if (a[mid] > key)//当要找到的key在中间值的左边时{right = mid-1;//右边界向后退一位,压缩寻找范围}elsereturn mid;//当key刚好等于中间值,返回该值}return -1;//遍历整个数组后,都没有找到合适值,说明该数组中没有要寻找的key值,返回-1;
}
int main()
{int k = 0;int arr[] = { 3,7,8,16,25,34,43,52,61,70 };while (1){scanf("%d", &k);int sz = sizeof(arr) / sizeof(arr[0]);if (find_t(arr, k, sz) != -1)printf("exist the number is:%d\n", find_t(arr, k, sz));elseprintf("no exist!\n");}return 0;
}

程序运行结果如下:

2. 计算数字在升序数组中出现的次数

一、方法一

暴力遍历,无视顺序

该方法无论有序无序,均适用。直接从第一个数字开始,遍历整个数组,一旦遇见目标值就+1,但该方法相对二分法较为费时,代码如下:

int GetNumberOfK(int* data, int dataLen, int k )
{int count=0;//定义一个count为0;for(int i=0;i<dataLen;i++){if(data[i]==k)//遇到与目标值k相同的就+1;count++;}return count;//返回该值
}

二、方法二

二分法查找

使用二分法查找,因为查找的数组有序,所以目标值如果有多个,肯定是连在一起,我们可以通过二分查找,找到该一串连续数字的左右边界,例如:

上述代码中,如果目标值为7,则左边界就是该段数组中的第一个7,右边界为该段数组中的最后一个7再加一位,即对应上图中的第一个8,用8的下标,减去第一个7的下标即为该数组中7的个数,即right-left.

所以,需要进行两次二分查找,分别找出左右边界,代码如下:

int GetNumberOfK(int* data, int dataLen, int k )
{int l=0,r=dataLen,left=0,right=0;while(l<r){//确定左界int mid=(r-l)/2+l;//计算中间值if(data[mid]<k)l=mid+1;elser=mid;}left=l;//重新赋值,再次进行一次二分查找,确定右界l=0;r=dataLen;while(l<r){int mid=(r-l)/2+l;//计算中间值if(data[mid]<=k)l=mid+1;elser=mid;}right=r;return right-left;//个数为右边界减去左边界
}

这里注意:

二分查找,可以用于查找边界值或者具体某一个目标值,第一部分举的二分法示例时找具体某一个值,而该题是寻找边界值,要注意在寻找边界值时,while中的判断部分是left<right,左右边界的每一次循环后的值要根据具体情况判断是=mid+(-)1,还是=mid;

【C语言】计算数字在升序数组中出现的次数的两种方法相关推荐

  1. 【牛客 - 剑指offer】JZ53 数字在升序数组中出现的次数 Java实现

    文章目录 剑指offer题解汇总 Java实现 本题链接 题目 方案一 暴力 方案二 二分(推荐) 剑指offer题解汇总 Java实现 https://blog.csdn.net/guligulig ...

  2. 牛客题霸 [ 数字在升序数组中出现的次数] C++题解/答案

    牛客题霸 [ 数字在升序数组中出现的次数] C++题解/答案 题目描述 统计一个数字在升序数组中出现的次数. 题解: 直接for循环,if判断一下,如果是目标的话ant++ 代码: class Sol ...

  3. 【C语言】数字在排序数组中出现的次数(改动)

    //数字在排序数组中出现的次数(改动) //统计一个数字在排序数组中出现的次数.比如:排序数组{1,2,3,3,3.3,4,5}和数字3,因为3出现了4次,因此输出4. #include <st ...

  4. js 判断数组中是否有重复值两种方法

    判断数组中是否有重复的值,重复则提示优先级重复 第一种方法 推荐 // 以数组值为键,持续向一个对象里面加值,// 如果在加值之前就发现这个属性在对象中已经存在,那么他就是重复的 function i ...

  5. 剑指Offer(Java版):数字在排序数组中出现的次数

    2019独角兽企业重金招聘Python工程师标准>>> 题目:统计一个数字在排序数组中出现的次数.例如输入排序数组为 {1,2,3,3,,3,3,4,5}和数字3,由于3在这个数组中 ...

  6. 【剑指offer】数字在排序数组中出现的次数

    转载请注明出处:http://blog.csdn.net/ns_code/article/details/27364557 题目描写叙述: 统计一个数字在排序数组中出现的次数. 输入: 每一个測试案例 ...

  7. 36数字在排序数组中出现的次数

    题目描述 统计一个数字在排序数组中出现的次数. 思路:记住二分搜索的复杂度是O(logn),复杂度的计算方式是主定理.二分搜索模板要记得. 这题要注意没有找到相关元素的返回情况,初始化的时候将两个位置 ...

  8. 剑指offer:数字在排序数组中出现的次数

    题目描述 统计一个数字在排序数组中出现的次数. 解题思路 暴力求解,没用到排序的已知条件. class Solution { public:int GetNumberOfK(vector<int ...

  9. 【剑指offer-Java版】38数字在排序数组中出现的次数

    数字在排序数组中出现的次数: 最简单粗暴的方法是O(n^2) 可能的解法可以采用二分,首先根据二分找到给定数字在数组中的位置,然后再左右二分,找到边界(第一个和最后一个),左右边界的差值就是出现次数 ...

最新文章

  1. (七)使用jedis连接单机和集群(一步一个坑踩出来的辛酸泪)
  2. MVC模式与三层架构的区别
  3. BigDecimal源码解析
  4. linux 脚本 if else,基于shell的if和else详解
  5. 这部纪录片央视发力了,每一帧都可以当壁纸,BBC也无法超越
  6. 牛客题霸 [两个链表生成相加链表] C++题解/答案
  7. arcore_如何使用ARCore和Android Studio构建增强现实Android应用
  8. java编程50_java经典50编程题(1-10)
  9. oracle和Linux能兼容吗,Oracle基于Linux 7下的安装
  10. 《浪潮之巅》读书笔记——第6章 Microsoft
  11. Airflow安装教程
  12. (美)梅耶(Myers, G. J.) 等《软件测试的艺术(原书第3版)》书籍(第3版)
  13. aic值检验 p值_qRT-PCR差异分析及P值计算
  14. 计算机无法正常更新,电脑时间不能自动更新怎么回事?电脑时间校准同步方法介绍...
  15. android双卡切换,OPPOReno双卡双待怎么切换使用?
  16. core dumped ?完了?
  17. 一个博士在华为的22年!
  18. oracle rebuild online,Oracle index rebuild online 与 rebuild 及 drop index 后重建
  19. 共识算法-Mencius详解
  20. 如何隐藏电脑硬盘分区

热门文章

  1. 人工智能最新研究发展方向——OCR文字识别简述
  2. 怎样才能做好PPT,驼峰设计给大学生的10条建议
  3. 计算机数学学院,16级软件学院《计算机数学》课程标准
  4. Java项目:springBoot+Vue汽车销售管理系统
  5. 如何给二维码动态插入图片
  6. 服务器端口映射到外网
  7. table表头固定方法
  8. APP(Android版)客户端与服务器端时间校准
  9. Android应用加固产品使用对比
  10. 策略迭代中的风险管理与合规性管理