美文网首页
2018暑假集训Problem Archive #1K题题解和感

2018暑假集训Problem Archive #1K题题解和感

作者: 谈的还原性 | 来源:发表于2018-07-30 09:56 被阅读0次

K题

题目大意

题目链接
给你一个大小为n的数组a,和数字k,求数组a中大小大于等于k的子数组的最大平均值


分析

先用一个循环来遍历子数组的头部,注意循环结束的条件,i<=n-k。再用一个循环来遍历子数组的尾部,对于每一个子数组,求出它的平均值,并不断更新,存储最大的平均值。但注意到题目中n和k的数据都比较大,在代码1中每次都去遍历子数组来求和,最终导致在第13个测试数据中就超时了,所以这道题就要用到前缀和来计算,在输入数据的时候就用另外一个数组来存储前i个数据的和,这样在求子数组和的时候就可以用sum=result[j+1]-result[i]直接求出和,简化了复杂度。


代码1

#include <cstdio>
#include <iostream>
#include <algorithm>
#include <string.h>
#define MAX_N 5000+5
using namespace std;
int main(int argc, char const *argv[])
{
    int n,k;
    int number[MAX_N];
    double res1,res2=0;
    scanf("%d%d",&n,&k);
    for(int i=0;i<n;i++)
    {
        scanf("%d",&number[i]);
    }
    for(int i=0;i<=n-k;i++)
    {
        for(int j=i+k-1;j<n;j++)
        {
            double sum=0;
            for(int m=i;m<=j;m++)
            {
                sum+=number[m];
            }
            res1=sum/(j-i+1);
            if(res1>res2)
                res2=res1;
        }
    }
    printf("%.15llf\n",res2);
    return 0;
}

代码2

#include <cstdio>
#include <iostream>
#include <algorithm>
#include <string.h>
#define MAX_N 5000+5
using namespace std;
int main(int argc, char const *argv[])
{
    int n,k;
    int number[MAX_N];
    int result[MAX_N];
    result[0]=0;
    double res1,res2=0;
    scanf("%d%d",&n,&k);
    for(int i=0;i<n;i++)
    {
        scanf("%d",&number[i]);
        result[i+1]=result[i]+number[i];
    }
    for(int i=0;i<=n-k;i++)
    {
        for(int j=i+k-1;j<n;j++)
        {
            double sum=result[j+1]-result[i];
            res1=sum/(j-i+1);
            if(res1>res2)
                res2=res1;
        }
    }
    printf("%.15llf\n",res2);
    return 0;
}

总结
前缀和很重要

相关文章

网友评论

      本文标题:2018暑假集训Problem Archive #1K题题解和感

      本文链接:https://www.haomeiwen.com/subject/wnexvftx.html