zoukankan      html  css  js  c++  java
  • poj3061 poj3320 poj2566尺取法基础(一)

    poj3061 给定一个序列找出最短的子序列长度,使得其和大于等于S

    那么只要用两个下标,区间和小于S时右端点向右移动,区间和大于S时左端点向右移动,在这个过程中更新Min

    #include <cstdio>
    #include <algorithm>
    #include <cstring>
    #define MAX 100005
    #define LL long long
    #define INF 0x3f3f3f3f
     
    using namespace std;
    LL a[100010];
    int n, t, ans = INF;
    LL sum, s;
     
    int main()
    {
        scanf("%d", &t);
        while (t--){
            scanf("%d %I64d", &n, &s);
            for (int i = 0; i < n; i++) scanf("%I64d", a+i);
            int st = 0, en = 0;
            ans = INF; sum = 0;
            while (1){
                while (en<n && sum<s) sum += a[en++];
                if (sum < s) break;
                ans = min(ans, en-st);
                sum -= a[st++];
            }
            if (ans == INF) ans = 0;
            printf("%d
    ", ans);
        }
        return 0;
    }

    poj3320给一本书有P页,每页都有一个知识点,求最少的连续页数覆盖所有知识点

    如果一个区间的子区间满足条件,那么右端点固定,左端点推进

    反之左端点固定 ,右端点推进么。需要用map进行映射,set求总共有多少知识点

    #include <cstdio>
    #include <algorithm>
    #include <cstring>
    #include <set>
    #include <map>
    #define MAX 1000010
    #define LL long long
    #define INF 0x3f3f3f3f
     
    using namespace std;
    int a[MAX];
    map <int, int> cnt;
    set <int> t;
    int p, ans = INF, st, en, sum;
     
    int main()
    {
        scanf("%d", &p);
        for (int i = 0; i < p; i++) scanf("%d", a+i), t.insert(a[i]);
        int num = t.size();
        while (1){
            while (en<p && sum<num)
                if (cnt[a[en++]]++ == 0) sum++;
            if (sum < num) break;
            ans = min(ans, en-st);
            if (--cnt[a[st++]] == 0) sum--;
        }
        printf("%d
    ", ans);
        return 0;
    }

    poj2566 给定一个数组和值t,求一个子区间使得其和的绝对值与t的差值最小

    有正有负,不能保证单调性,无法单点拓展边界,预处理出所有的前缀和,升序排列

    然后尺取法求出两个端点,使区间和的绝对值最逼近t

    #include <cstdio>
    #include <algorithm>
    #include <cstring>
    #define INF 0x3f3f3f3f
    #define LL long long
    #define MAX 100010
    using namespace std;
     
    typedef pair<LL, int> p;
    LL a[MAX], t, ans, tmp, b;
    int n, k, l, u, st, en;
    p sum[MAX];
     
    LL myabs(LL x)
    {
        return x>=0? x:-x;
    }
     
    int main()
    {
        while (scanf("%d %d", &n, &k), n+k){
            sum[0] = p(0, 0);
            for (int i = 1; i <= n; i++){
                scanf("%I64d", a+i);
                sum[i] = p(sum[i-1].first+a[i], i);
            }
            sort(sum, sum+1+n);
            while (k--){
                scanf("%I64d", &t);
                tmp = INF; st = 0, en = 1;
                while(en <= n){
                    b = sum[en].first-sum[st].first;
                    if(myabs(t-b) < tmp){
                        tmp = myabs(t-b);
                        ans = b;
                        l = sum[st].second; u = sum[en].second;
                    }
                    if(b > t) st++;
                    else if(b < t) en++;
                    else break;
                    if(st == en) en++;
                }
                if (u < l) swap(u, l);
                printf("%I64d %d %d
    ", ans, l+1, u);
            }
        }
        return 0;
    }
  • 相关阅读:
    CDN使用心得
    IIS6.0实现SSL安全加密
    从print css谈样式表的媒介(media)属性
    ASP.NET文件下载各种方式比较:对性能的影响、对大文件的支持、对断点续传和多线程下载的支持
    “同名Cookie”的分析
    周末部门游玩顺德碧桂园度假村
    Linux特殊文件权限
    周末部门游玩广州长隆欢乐世界
    开个博客
    iOS TableView数据绑定的原则
  • 原文地址:https://www.cnblogs.com/zsben991126/p/10134576.html
Copyright © 2011-2022 走看看