• 51nod-1065 最小正子段和 【贪心 + 思维】


    N个整数组成的序列a[1],a[2],a[3],…,a[n],从中选出一个子序列(a[i],a[i+1],…a[j]),使这个子序列的和>0,并且这个和是所有和>0的子序列中最小的。
    例如:4,-1,5,-2,-1,2,6,-2。-1,5,-2,-1,序列和为1,是最小的。
     
    Input
    第1行:整数序列的长度N(2 <= N <= 50000)
    第2 - N+1行:N个整数
    Output
    输出最小正子段和。
    Input示例
    8
    4
    -1
    5
    -2
    -1
    2
    6
    -2
    Output示例
    1


    解题思路:记录前缀累加和,然后排序,检查相邻的两项是否能够组成子序列,可以的话就记录该值D,记录最小的D就是结果。
    排序的目的是找到前缀和最接近的数。
    附ac代码:
     1 #include <cstdio>
     2 #include <cstring>
     3 #include <algorithm>
     4 #include <string>
     5 #include <cmath>
     6 #include <string>
     7 #include <iostream>
     8 #include <map>
     9 #include <queue>
    10 const int maxn = 5 * 1e4 + 10;
    11 const int inf = 0x3f3f3f3f;
    12 
    13 using namespace std;
    14 typedef long long ll;
    15 const ll mod = 1e9 + 7;
    16 ll nu[maxn];
    17 struct nod {
    18     int r;
    19     ll sum;
    20 }ans[maxn];
    21 bool cmp(nod a, nod b) {
    22     if(a.sum < b.sum) return 1;
    23     else if(a.sum == b.sum && a.r < b.r) return 1;
    24     return 0;
    25 }
    26 int main(int argc, const char * argv[]) {
    27    // int t;
    28     int n;
    29     scanf("%d", &n);
    30     ll minn = inf;
    31     for(int i = 1; i <= n; ++i) {
    32         scanf("%lld", &nu[i]);
    33         ans[i].sum = ans[i - 1].sum + nu[i];
    34         ans[i].r = i;
    35         if(nu[i] > 0)
    36         minn = min(nu[i], minn);
    37         if(ans[i].sum > 0)
    38         minn = min(ans[i].sum, minn);
    39     }
    40   //  printf("%lld %lld xxxx
    ", ans[2].sum, minn);
    41     sort(ans + 1, ans + 1 + n, cmp);
    42 
    43 
    44     for(int i = 2; i <= n; ++i) {
    45         if(ans[i].r > ans[i - 1].r && ans[i].sum - ans[i - 1].sum > 0)
    46         minn = min(minn, ans[i].sum - ans[i - 1].sum);
    47         if(ans[i].r < ans[i - 1].r && ans[i - 1].sum - ans[i].sum > 0)
    48         minn = min(minn, ans[i - 1].sum - ans[i].sum);
    49 
    50     }
    51     if(minn == inf) puts("no solution");
    52     else
    53     printf("%lld
    ", minn);
    54     return 0;
    55 }
    View Code
  • 相关阅读:
    c# 使用 Read 读取数据块
    C# TCP/IP通信,Socket通信例子
    c# virtual 关键字 虚方法
    统计图
    oauth2.0 判断接口是否允许跨域
    OI常用模板合集
    CSP2021游记
    8.16 树上问题模拟赛总结
    8.15 图论模拟赛垫底记
    8.14 字符串模拟赛总结
  • 原文地址:https://www.cnblogs.com/zmin/p/9029895.html
Copyright © 2020-2023  润新知