zoukankan      html  css  js  c++  java
  • 涨姿势之区间刷新

    涨姿势之区间刷新

    TimeLimit:2000MS  Memo
     1 #include <iostream>
     2 #include <cstring>
     3 #include <algorithm>
     4 
     5 using namespace std;
     6 
     7 typedef long long ll;
     8 const int N=1e6+6;
     9 
    10 int arr[N],sum[N];
    11 int t,n,m,s,w;
    12 
    13 int main(){
    14     ios::sync_with_stdio(false);
    15     cin>>t;
    16     while(t--){
    17         memset(arr,0,sizeof(arr));
    18         memset(sum,0,sizeof(sum));
    19         cin>>n>>m>>s>>w;
    20         while(m--){
    21             int x,y;
    22             cin>>x>>y;
    23             arr[x]++,arr[y+1]--;
    24         }   //这里优化了一下时间复杂度
    25         for(int i=1;i<=n;i++){
    26             arr[i]+=arr[i-1];
    27         }
    28         for(int i=1;i<=n;i++){   //求前缀和
    29             sum[i]=sum[i-1]+arr[i];
    30         }
    31 //        for(int i=1;i<=n;i++) cout << sum[i] << endl;
    32         ll res=0,l=1,r=1;  //双指针从一开始
    33         for(int i=1;i<=n;i++){
    34             while(r<i&&sum[i]-sum[r]>=w){
    35                 r++;
    36             }
    37             while(l-1<r-1&&sum[r-1]-sum[l-1]>=w&&sum[i]-sum[l-1]>=s){   //l-1是符合的
    38                 l++;
    39             }
    40             if(l-2<r-1&&sum[i]-sum[r-1]>=w&&sum[r-1]-sum[l-2]>=w&&sum[i]-sum[l-2]>=s){
    41                 res+=l-1;
    42 //                cout << "  " <<  res << "  " << endl;
    43             }
    44         }
    45         cout << res << endl;
    46     }
    47     return 0;
    48 }
    View Code
    ryLimit:128MB
    64-bit integer IO format:%lld
    已解决 | 点击收藏 | 已有4人收藏了本题
    Problem Description

    Value_Dragon是一个有钱人。快过年了,所以他准备发红包。但是他发红包的方式很奇葩。他让n个人排成一排。每次选择1-n中的一段区间[l,r]发,给区间中的每一个人一块钱。就这样发了m次红包。发完后他想知道在[1,n]的子区间中有多少个区间满足以下要求

    1. 这个区间得到钱的总数不少于s

    2. 这个区间可以被分成两个不相交的子区间且每个子区间得到的钱的总数不小于w

    (注:一个区间的子区间包括自己本身)

    防坑提醒,长度为1的区间比如[1,1],是不能被拆成两个子区间的

    Input

    第一行是一个整数T代表数据的组数。
    接下来有T组数据
    每组数据开头有四个整数,分别代表n m s w
    接下来m行,每行是是两个数l,r代表区间[l,r]的左右端点

    其中T<=10

    n<=10^6,m<=10^5

    0<l<=r<=n

    0<=w<=s<10^8

    Output

    对于每组数据输出一行,代表符合要求的区间个数

    SampleInput
    4
    1 0 0 0
    
    1000000 0 0 0
    
    1000000 1 0 0
    1 1000000
    
    10 10 20 14
    2 10
    5 9
    5 5
    6 8
    2 6
    9 10
    6 7
    6 10
    4 5
    5 7
    
    SampleOutput
    0
    499999500000
    499999500000
    8

  • 相关阅读:
    C *p++ (*p)++ *p+=2 区别
    C 找到两字串中最长的相同串
    Jquery插件Jquerycolor
    C Fibonacci前N项和 阶乘的前N项和
    Baidu Google地图应用
    6.11Java多线程、并发、同步、synchronized方法
    6.10Java线程同步_synchronized
    6.18Java多线程并发、同步性能分析
    6.11Java多线程、并发、同步、synchronized块
    6.18Java多线程同步方法实现DemoNo2
  • 原文地址:https://www.cnblogs.com/qq-1585047819/p/11272294.html
Copyright © 2011-2022 走看看