2 条题解

  • 0
    @ 2025-10-8 16:55:20

    A18 双指针(尺取法)
    A18 双指针(尺取法)(内网)

    #include<bits/stdc++.h>
    using namespace std;
    
    int n,m,a[1000005];
    int cnt[2005],num,len,l,r;
    //a[i]  表示第i幅画的画家编号
    //cnt[k]表示当前区间画家k的图画数
    //num 记录当前区间有多少画家
    //len 记录合法区间长度
    //l,r 记录合法区间的左右端点
    
    int main(){
      scanf("%d%d",&n,&m);
      for(int i=1;i<=n;i++) scanf("%d",&a[i]);
      
      cnt[a[1]]=1; num=1; len=1000005;
      for(int j=1,i=1; j<=n;){   //i<=j
        if(num<m){
          j++; 
          cnt[a[j]]++;
          if(cnt[a[j]]==1) num++;
        }      
        if(num==m){
          if(len>j-i+1){
            len=j-i+1; l=i; r=j; //更新
          }
          cnt[a[i]]--;
          if(cnt[a[i]]==0) num--;
          i++;
        }
      }
      printf("%d %d\n",l,r);
      return 0;
    • 0
      @ 2025-10-8 16:55:08

      A18 双指针(尺取法)

      A18 双指针(尺取法)(内网)

      #include<bits/stdc++.h>
      using namespace std;
      
      int n,m,a[1000005];
      int cnt[2005],num,len,l,r;
      //a[i]  表示第i幅画的画家编号
      //cnt[k]表示当前区间画家k的图画数
      //num 记录当前区间有多少画家
      //len 记录合法区间长度
      //l,r 记录合法区间的左右端点
      
      int main(){
        scanf("%d%d",&n,&m);
        for(int i=1;i<=n;i++) scanf("%d",&a[i]);
        
        cnt[a[1]]=1; num=1; len=1000005;
        for(int j=1,i=1; j<=n;){   //i<=j
          if(num<m){
            j++; 
            cnt[a[j]]++;
            if(cnt[a[j]]==1) num++;
          }      
          if(num==m){
            if(len>j-i+1){
              len=j-i+1; l=i; r=j; //更新
            }
            cnt[a[i]]--;
            if(cnt[a[i]]==0) num--;
            i++;
          }
        }
        printf("%d %d\n",l,r);
        return 0;
      }
      • 1

      A18 双指针(尺取法) 最小全覆盖区间[逛画展]

      信息

      ID
      1072
      时间
      1000ms
      内存
      512MiB
      难度
      6
      标签
      递交数
      104
      已通过
      30
      上传者