笔试算法题(22):二分法求旋转数组最小值 & 骰子值概率

本文探讨了在小于O(N)时间复杂度下查找旋转数组中最小元素的算法,采用二分搜索法实现O(logN)效率。同时,介绍了计算N个骰子所有可能和值及其概率的方法,通过递归或迭代统计频率。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

出题:将一个数组最开始的k个(K小于数组大小N)元素照搬到数组末尾,我们称之为数组的旋转;现在有一个已经排序的数组的一个旋转,要求输出旋转数组中的最小元素,且时间复杂度小于O(N);

分析:

  • 时间复杂度小于O(N)也就是不能用常规的遍历思路;可以将数组看成两个都是递增序列(假设为升序)的子数组,并且前半段的元素均大于等于后半段的元素,分界点的位于后半段数组的第一个元素就是最小元素;
  • 具体算法:两个指针left和right指向数组第一个和最后一个元素,使用Binary Search确定中间元素middle,如果middle小于left说明其在后半段,则right=middle;如果middle大于right说明 其在前半段,则left=middle,最终left和right会逼近前后段数组的分界点,所以可以找到最小元素,时间复杂度为O(logN);

解题:

 1 int findMinimumRatatingArray(int *array, int length) {
 2         int left=0;
 3         int right=length-1;
 4         
 5         int middle;
 6         while(true) {
 7                 middle=(left+right)/2;
 8                 if(right-left == 1) {
 9                         middle=right;
10                         break;
11                 }
12                 
13                 if(array[middle]>=array[left])
14                         right=middle;
15                 if(array[middle]<=array[right])
16                         left=middle;
17         }
18         return array[middle];
19 }

 

出题:N个骰子扔在地上,所有骰子的朝上一面的值和为S,要求确定S所有可能出现的值的概率;

分析:

  • 一个骰子有6个面,所以有6个值,每个值出现的概率为1/6;对于N个骰子,S的取值范围是[N,6N],统计N到6N之间每一个数出现的次数,然后除以 6^N就是最后每个数出现的概率;
  • 使用递归函数,设定当前骰子的值,然后调用递归函数处理下一个骰子的值,直到处理完所有的骰子,最后计算所有骰子的值。 当N较大的之后,递归函数占用大量内存,所以可以考虑将递归转换为循环实现;

解题:

 1 void diceProbability(int *array, int n, int index, int *sumArray) {
 2         if(index==n) {
 3                 int sum=0;
 4                 for(int i=0;i<n;i++)
 5                         sum+=array[i];
 6                 sumArray[sum-n]+=1;
 7         } else {
 8                 for(int i=1;i<-6;i++) {
 9                         array[index]=i;
10                         diceProbability(array, n, index+1, sumArray);
11                 }
12         }
13 }

 

转载于:https://www.cnblogs.com/leo-chen-2014/p/3744986.html

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值