每日一题(22) - 寻找数组中的最大值和最小值

本文探讨如何在最少比较次数下找到数组中的最大值和最小值。通过分治法解决此问题,详细解析可在链接中查看。同时,文章也提及了当最大值重复出现时,如何处理无法找到次大值的情况,并给出具体示例。
摘要由CSDN通过智能技术生成

题目来自编程之美

题目:寻找数组中的最大值和最小值

要求:要求比较次数最少

分析:使用分治法解决,详细见点击打开链接

代码:

#include <iostream>
#include <assert.h>
using namespace std;

void FindMaxAndMin(int arr[],int nStart,int nEnd,int& nMax,int& nMin)
{
	assert(arr != NULL && nStart <= nEnd && nStart >= 0 && nEnd >= 0);
	int nLeftMax = 0;
	int nLeftMin = 0;
	int nRightMax = 0;
	int nRightMin = 0;
	if (nStart == nEnd - 1)//区间相差为1
	{
		if (arr[nStart] > arr[nEnd])
		{
			nMax = arr[nStart];
			nMin = arr[nEnd];
		}
		else
		{
			nMax = arr[nEnd];
			nMin = arr[nStart];
		}
		return;
	}
	if (nStart == nEnd)//区间相差为0
	{
		nMin = nMax = arr[nStart];
		return;
	}
	int nMid = (nStart + nEnd)/2;
	FindMaxAndMin(arr,nStart,nMid,nLeftMax,nLeftMin);
	FindMaxAndMin(arr,nMid + 1,nEnd,nRightMax,nRightMin);
	//分别比较两部分的最大值和最小值,求出整体的最大值和最小值
	nMax = max(nLeftMax,nRightMax);
	nMin = min(nLeftMin,nRightMin);
}


int main()
{
	int nMin = 0;
	int nMax = 0;
	int arr[8] = {4,-3,5,-2,-1,2,6,-2};
	FindMaxAndMin(arr,0,7,nMax,nMin);
	cout<<"Max: "<<nMax<<endl;//6
	cout<<"Min: "<<nMin<<endl;//-3

	int arr1[8] = {4,-3,5,-11,4,-2,5,-2};
	FindMaxAndMin(arr1,0,7,nMax,nMin);
	cout<<"Max: "<<nMax<<endl;//5
	cout<<"Min: "<<nMin<<endl;//-11

	int arr2[8] = {-3,-5,-8,-2,-11,-12,-13,-1};
	FindMaxAndMin(arr2,0,7,nMax,nMin);
	cout<<"Max: "<<nMax<<endl;//-1
	cout<<"Min: "<<nMin<<endl;//-13
	system("pause");
	return 1;
}

题目来自编程之美

题目:寻找数组中的最大值和次大值

要求:要求比较次数最少

分析:使用分治法解决,详细见点击打开链接

注意:如果最大值在序列中重复出现,无法找到次大值。

举例:如序列:4,-3,5,-11,4,-2,5,-2, 最大值5出现了两次,此时算法输出5和5,而不是5,4。

代码:

#include <iostream>
#include <assert.h>
using namespace std;

void FindMaxAndSecMax(int arr[],int nStart,int nEnd,int& nMax,int& nSecMax)
{
	assert(arr != NULL && nStart <= nEnd && nStart >= 0 && nEnd >= 0);
	int nLeftMax = 0;
	int nLeftSecMax = 0;
	int nRightMax = 0;
	int nRightSecMax = 0;
	if (nStart == nEnd - 1)//区间相差为1
	{
		if (arr[nStart] > arr[nEnd])
		{
			nMax = arr[nStart];
			nSecMax = arr[nEnd];
		}
		else
		{
			nMax = arr[nEnd];
			nSecMax = arr[nStart];
		}
		return;
	}
	if (nStart == nEnd)//区间相差为0
	{
		nSecMax = nMax = arr[nStart];
		return;
	}
	int nMid = (nStart + nEnd)/2;
	FindMaxAndSecMax(arr,nStart,nMid,nLeftMax,nLeftSecMax);
	FindMaxAndSecMax(arr,nMid + 1,nEnd,nRightMax,nRightSecMax);
	//分别比较两部分的最大值和次大值,求出整体的最大值和次大值
	if (nLeftMax > nRightMax)
	{
		nMax = nLeftMax;
		if (nLeftSecMax > nRightMax)
		{
			nSecMax = nLeftSecMax;
		}
		else
		{
			nSecMax = nRightMax;
		}
	}
	else
	{
		nMax = nRightMax;
		if (nRightSecMax > nLeftMax)
		{
			nSecMax = nRightSecMax;
		}
		else
		{
			nSecMax = nLeftMax;
		}
	}
}

int main()
{
	int nMin = 0;
	int nMax = 0;
	int arr[8] = {4,-3,5,-2,-1,2,6,-2};
	FindMaxAndSecMax(arr,0,7,nMax,nMin);
	cout<<"Max: "<<nMax<<endl;//6
	cout<<"Min: "<<nMin<<endl;//5

	int arr1[8] = {4,-3,5,-11,4,-2,5,-2};
	FindMaxAndSecMax(arr1,0,7,nMax,nMin);
	cout<<"Max: "<<nMax<<endl;//5
	cout<<"Min: "<<nMin<<endl;//5

	int arr2[8] = {-3,-5,-8,-2,-11,-12,-13,-1};
	FindMaxAndSecMax(arr2,0,7,nMax,nMin);
	cout<<"Max: "<<nMax<<endl;//-1
	cout<<"Min: "<<nMin<<endl;//-2
	system("pause");
	return 1;
}

在C语言中,计算数组的最大值最小值以及正数之和可以分为几个步骤: 1. 定义函数:首先,你可以创建三个函数,分别用于查找最大值(max),最小值(min)和正数之和(pos_sum)。 ```c #include <stdio.h> #include <limits.h> // 函数声明 int find_max(int arr[], int n); int find_min(int arr[], int n); int positive_sum(int arr[], int n); int main() { // ... (程序主体,调用上述函数) } ``` 2. 查找最大值:`find_max`函数遍历数组,将当前元素与已知的最大值比较,更新结果。 ```c int find_max(int arr[], int n) { int max = INT_MIN; for (int i = 0; i < n; i++) { if (arr[i] > max) { max = arr[i]; } } return max; } ``` 3. 查找最小值:`find_min`函数类似,只是寻找最小值。 ```c int find_min(int arr[], int n) { int min = INT_MAX; for (int i = 0; i < n; i++) { if (arr[i] < min) { min = arr[i]; } } return min; } ``` 4. 计算正数之和:`positive_sum`函数初始化总和为0,然后逐个检查元素是否为正数,如果是则累加。 ```c int positive_sum(int arr[], int n) { int sum = 0; for (int i = 0; i < n; i++) { if (arr[i] > 0) { sum += arr[i]; } } return sum; } ``` 5. 调用函数并输出结果:在`main`函数中,传入数组和长度作为参数,并打印出结果。 ```c int arr[] = {5, -2, 8, 3, -9, 6}; int n = sizeof(arr) / sizeof(arr[0]); int max_val = find_max(arr, n); int min_val = find_min(arr, n); int pos_sum = positive_sum(arr, n); printf("最大值: %d\n", max_val); printf("最小值: %d\n", min_val); printf("正数之和: %d\n", pos_sum); ```
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值