zoukankan      html  css  js  c++  java
  • 【Foreign】朗格拉日计数 [暴力]

    朗格拉日计算

    Time Limit: 10 Sec  Memory Limit: 128 MB

    Description

      

    Input

      

    Output

      仅一行一个整数表示答案。

    Sample Input

      5
      3 2 5 4 1

    Sample Output

      4

    HINT

      

    Main idea

      将一个排列围成一个环,每个点有一个值a[i],若顺时针三个点A、B、C 满足 a[A]<a[B]<a[C] 则可以统计答案,询问答案。

    Solution

      我们不考虑环,从序列考虑,显然可以统计的就是类似这种:123、231、312这个样子的。

      我们考虑容斥,显然123这种是可以直接计算的,231就是xx1 - 321,312就是3xx - 321。

      显然我们这样这样用树状数组统计一下 f[i] 表示 i 前面<a[i]的个数,然后就可以计算出:前面<a[i]的个数、前面>a[i]的个数、后面<a[i]的个数、后面>a[i]的个数

      然后这样暴力计算即可。

    Code

     1 #include<iostream>  
     2 #include<algorithm>  
     3 #include<cstdio>  
     4 #include<cstring>  
     5 #include<cstdlib>  
     6 #include<cmath>  
     7 using namespace std;
     8 typedef long long s64;
     9 const int ONE = 1000001;
    10 const int MOD = 1e9+7;
    11 
    12 int n;
    13 int a[ONE],f[ONE];
    14 s64 Ans;
    15 
    16 int get()
    17 { 
    18         int res=1,Q=1;    char c;
    19         while( (c=getchar())<48 || c>57)
    20         if(c=='-')Q=-1;
    21         if(Q) res=c-48; 
    22         while((c=getchar())>=48 && c<=57) 
    23         res=res*10+c-48; 
    24         return res*Q; 
    25 }
    26 
    27 s64 C(int n)
    28 {
    29         return (s64)n*(n-1)/2;
    30 }
    31 
    32 
    33 namespace Bit
    34 {
    35         int C[ONE];
    36         
    37         int lowbit(int x)
    38         {
    39             return x&-x;
    40         }
    41     
    42         void Add(int R,int x)
    43         {
    44             for(int i=R;i<=n;i+=lowbit(i))
    45                 C[i]+=x;
    46         }
    47         
    48         int Query(int R)
    49         {
    50             int res=0;
    51             for(int i=R;i>=1;i-=lowbit(i))    
    52                 res+=C[i];
    53             return res;
    54         }
    55 }
    56 
    57 int pre_min(int i) {return f[i];}
    58 int pre_max(int i) {return i-1-f[i];}
    59 int suc_min(int i) {return a[i]-1-pre_min(i);}
    60 int suc_max(int i) {return n-a[i]-pre_max(i);}
    61 
    62 int main()
    63 {
    64         n=get();
    65         for(int i=1;i<=n;i++)    a[i]=get();
    66         
    67         for(int i=1;i<=n;i++)
    68         {
    69             Bit::Add(a[i],1);
    70             f[i] = Bit::Query(a[i]-1);
    71         }
    72         
    73         for(int i=1;i<=n;i++)
    74         {
    75             Ans += (s64)pre_min(i) * suc_max(i);
    76             Ans += C( pre_max(i) );
    77             Ans += C( suc_min(i) );
    78             Ans -= (s64)2 * pre_max(i) * suc_min(i); 
    79         }
    80         
    81         printf("%lld",Ans);
    82 }
    View Code

     

  • 相关阅读:
    JAVAWE第一天
    01--2048实例开篇
    10--动作系统(四)动作类中的reverse方法
    09--动作系统(三)使用持续动作
    08--动作系统(二)使用即时动作
    【转】cocos2d-x windows开发环境配置
    07--动作系统(一)
    06--触摸事件响应
    05--简单场景切换与精灵创建
    04--简单菜单使用
  • 原文地址:https://www.cnblogs.com/BearChild/p/6522835.html
Copyright © 2011-2022 走看看