zoukankan      html  css  js  c++  java
  • 尺取法 POJ 3601 Subsequence

    题目传送门

     1 /*
     2     题意:求连续子序列的和不小于s的长度的最小值
     3     尺取法:对数组保存一组下标(起点,终点),使用两端点得到答案
     4         1. 记录前i项的总和,求[i, p)长度的最小值,用二分找到sum[p] - s[i] >= s的p
     5         2. 除了O (nlogn)的方法,还可以在O (n)实现,[i, j)的区间求和,移动两端点,更新最小值,真的像尺取虫在爬:)
     6 */
     7 #include <cstdio>
     8 #include <algorithm>
     9 #include <cstring>
    10 #include <cmath>
    11 using namespace std;
    12 
    13 typedef long long ll;
    14 const int MAXN = 1e5 + 10;
    15 const int INF = 0x3f3f3f3f;
    16 int a[MAXN];
    17 ll sum[MAXN];
    18 
    19 int main(void)        //POJ 3601 Subsequence
    20 {
    21     int t;    scanf ("%d", &t);
    22     while (t--)
    23     {
    24         memset (sum, 0, sizeof (sum));
    25         int n, s;
    26         scanf ("%d%d", &n, &s);
    27         for (int i=1; i<=n; ++i)    {scanf ("%d", &a[i]);    sum[i] = sum[i-1] + a[i];}
    28 
    29         if (sum[n] < s)    {puts ("0");    continue;}
    30 
    31         int ans = n;
    32         for (int i=1; sum[i]+s<=sum[n]; ++i)
    33         {
    34             int p = lower_bound (sum+i, sum+1+n, sum[i] + s) - sum;
    35             ans = min (ans, p - i);
    36         }
    37 
    38         printf ("%d
    ", ans);
    39     }
    40 
    41     return 0;
    42 }
    43 
    44 
    45 /*
    46 2
    47 10 15
    48 5 1 3 5 10 7 4 9 2 8
    49 5 11
    50 1 2 3 4 5
    51 */
     1 #include <cstdio>
     2 #include <algorithm>
     3 #include <cstring>
     4 #include <cmath>
     5 using namespace std;
     6 
     7 typedef long long ll;
     8 const int MAXN = 1e5 + 10;
     9 const int INF = 0x3f3f3f3f;
    10 int a[MAXN];
    11 
    12 int main(void)        //POJ 3601 Subsequence
    13 {
    14     int t;    scanf ("%d", &t);
    15     while (t--)
    16     {
    17         int n, s;
    18         scanf ("%d%d", &n, &s);
    19         for (int i=1; i<=n; ++i)    scanf ("%d", &a[i]);
    20 
    21         int ans = n + 1;    int i = 1, j = 1;    ll sum = 0;
    22         while (1)
    23         {
    24             while (j <= n && sum < s)    sum += a[j++];
    25             if (sum < s)    break;
    26             ans = min (ans, j - i);
    27             sum -= a[i++];
    28         }
    29 
    30         if (ans == n + 1)    puts ("0");
    31         else    printf ("%d
    ", ans);
    32     }
    33 
    34     return 0;
    35 }
    36 
    37 
    38 /*
    39 2
    40 10 15
    41 5 1 3 5 10 7 4 9 2 8
    42 5 11
    43 1 2 3 4 5
    44 */
    O (n)
    编译人生,运行世界!
  • 相关阅读:
    解决MySQL报错:1 of ORDER BY clause is not in GROUP BY clause and contains nonaggregated column 'informat
    安装KubeSphere
    kubesphere 安装
    正则表达式在线测试
    爬虫与Python:(二)Python基础篇——扩展:实现九九乘法表
    为什么 Python 的 Range 要设计成左开右闭区间?
    Python内置函数之range()
    爬虫与Python:(二)Python基础篇——13.类
    爬虫与Python:(二)Python基础篇——12.函数
    CSS之text-align
  • 原文地址:https://www.cnblogs.com/Running-Time/p/4550206.html
Copyright © 2011-2022 走看看