zoukankan      html  css  js  c++  java
  • 【BZOJ 4361】 4361: isn (DP+树状数组+容斥)

    4361: isn

    Time Limit: 10 Sec  Memory Limit: 256 MB
    Submit: 218  Solved: 126

    Description

    给出一个长度为n的序列A(A1,A2...AN)。如果序列A不是非降的,你必须从中删去一个数,
    这一操作,直到A非降为止。求有多少种不同的操作方案,答案模10^9+7。

    Input

    第一行一个整数n。
    接下来一行n个整数,描述A。

    Output

    一行一个整数,描述答案。

    Sample Input

    4
    1 7 5 3

    Sample Output

    18

    HINT

    1<=N<=2000

    Source

    【分析】

      考虑倒着想。

      你倒数第一步做之前还不是非降,做完之后就非降了,说明如果有一个上升序列,你加倒数第一个点时候不是上升序列了,前面的操作就可以任意了。

      本来想保证这个的,但是发现放入DP里还有一个关于长度的阶乘,根本不行。

      然后考虑容斥。

      现在的问题是:倒数第一个点x,放入序列里面还是非降的,这个时候不应该计算。

      即操作结束在更之前。把这些不合法的减掉就好了。

      g[i]表示长度为i的上升序列个数

      那么贡献就是$g[i]*(n-i)!-g[i+1]*(i+1)*(n-i-1)!$

     

     1 #include<cstdio>
     2 #include<cstdlib>
     3 #include<cstring>
     4 #include<iostream>
     5 #include<algorithm>
     6 using namespace std;
     7 #define Maxn 2010
     8 #define Mod 1000000007
     9 // #define LL long long
    10 
    11 int f[Maxn][Maxn],g[Maxn],fac[Maxn],c[Maxn],a[Maxn];
    12 
    13 struct node {int x,id;}t[Maxn];
    14 bool cmp(node x,node y) {return x.x<y.x;}
    15 
    16 int mx;
    17 void add(int x,int y)
    18 {
    19     for(int i=x;i<=mx;i+=i&(-i))
    20     {
    21         c[i]=(c[i]+y)%Mod;
    22     }
    23 }
    24 
    25 int get_sum(int x)
    26 {
    27     int ans=0;
    28     for(int i=x;i>=1;i-=i&(-i))
    29      ans=(ans+c[i])%Mod;
    30     return ans;
    31 }
    32 
    33 int main()
    34 {
    35     int n;
    36     scanf("%d",&n);
    37     for(int i=1;i<=n;i++)
    38     {
    39         int x;scanf("%d",&x);
    40         t[i].x=x;t[i].id=i;
    41     }
    42     sort(t+1,t+1+n,cmp);
    43     mx=1;a[t[1].id]=1;
    44     for(int i=2;i<=n;i++)
    45     {
    46         if(t[i].x!=t[i-1].x) mx++;
    47         a[t[i].id]=mx;
    48     }
    49     for(int i=1;i<=n;i++) f[1][i]=1;
    50     for(int i=2;i<=n;i++)
    51     {
    52         for(int j=0;j<=n;j++) c[j]=0;
    53         for(int j=1;j<=n;j++)
    54         {
    55             f[i][j]=get_sum(a[j]);
    56             add(a[j],f[i-1][j]);
    57         }
    58     }
    59     for(int i=1;i<=n;i++) for(int j=1;j<=n;j++) g[i]=(g[i]+f[i][j])%Mod;
    60     fac[0]=1;for(int i=1;i<=n;i++) fac[i]=1LL*fac[i-1]*i%Mod;
    61     int ans=0;
    62     ans=(ans+g[n]);
    63     for(int i=1;i<n;i++)
    64     {
    65         ans=(ans+1LL*g[i]*fac[n-i]%Mod-1LL*fac[n-i-1]*g[i+1]%Mod*(i+1)%Mod)%Mod;
    66     }
    67     ans=(ans+Mod)%Mod;
    68     printf("%d
    ",ans);
    69     return 0;
    70 }
    View Code

    2017-04-20 17:01:57

  • 相关阅读:
    dede cms 怎样调用年月日
    织梦自定义表单提交成功后提示信息|跳转页面|跳转停留时间修改全攻略
    springmvc入门
    git全面理解
    mac os中try catch快捷键
    git与github关联
    mac下apache服务器访问DocumentRoot目录后报Forbidden错误
    分布式处理框架MapReduce
    资源调度框架YARN
    异常:failed on connection exception: java.net.ConnectException:
  • 原文地址:https://www.cnblogs.com/Konjakmoyu/p/6739705.html
Copyright © 2011-2022 走看看