[CTSC2008]圖騰
阿新 • • 發佈:2019-01-12
傳送門
雖然是遠古時期的ctsc,但是果然還是ctsc啊
前置芝士:樹狀陣列
這個題最開始的思路很好想,由於之前寫過一個類似處理的題,所以這個題我一開始就想到了思路。
首先,我們可以嘗試講圖騰表示為xxxx的形式
那麼閃電就是:1324;高山是:1243和1432
ans=1324-1243-1432
然後應該容斥一下,但是我不會了。。
瞄一眼題解,我成功吧那個式子容斥出來了。
ans=1324-1243-1432
ans=(1x2x-1423)-(14xx-1423)-(12xx-1234)
ans=1x2x-14xx-12xx+1234
ans=1x2x-1xxx+13xx+1234
然後我就震驚的發現,我又不會了,這次變成仔細的研究題解了,各種討論情況啊,nb啊,大佬們
下面的討論情況還是看洛谷題解的吧,太難寫了。題解傳送門
程式碼:
#include<cstdio> #include<iostream> #include<cstring> using namespace std; void read(int &x) { char ch; bool ok; for(ok=0,ch=getchar(); !isdigit(ch); ch=getchar()) if(ch=='-') ok=1; for(x=0; isdigit(ch); x=x*10+ch-'0',ch=getchar()); if(ok) x=-x; } #define rg register #define lowbit(i) (i&(-i)) #define ls (get(a[i])) #define rs (a[i]-1-ls) #define lb (i-1-l[i]) #define rb (n-i-r[i]) const int mod=16777216,maxn=2e5+1; int n,ans,a[maxn],f[maxn],now,l[maxn],r[maxn]; void add(int x,int y){for(rg int i=x;i<=n;i+=lowbit(i))(f[i]+=y)%=mod;} int get(int x){int ans=0;for(rg int i=x;i;i-=lowbit(i))ans+=f[i];return ans;} int C(int n,int m){return 1ll*n*(n-1)*(n-2)/6%mod;} int main() { read(n); for(rg int i=1;i<=n;i++)read(a[i]),l[i]=ls,r[i]=a[i]-1-l[i],add(a[i],1); memset(f,0,sizeof f); for(rg int i=1;i<=n;i++) { ans=((ans+(l[i]*(i-1)-get(a[i])-l[i]*(l[i]-1)/2)*rb)%mod+mod)%mod, ans=((ans-C(rb,3))%mod+mod)%mod; add(a[i],i); } memset(f,0,sizeof f); for(rg int i=n;i;i--)ans=((ans+(1ll*get(a[i])-1ll*r[i]*(r[i]-1)/2)*rb)%mod+mod)%mod,add(a[i],a[i]-1); memset(f,0,sizeof f);now=0; for(rg int i=1;i<=n;i++)ans=(ans+1ll*rb*get(a[i]))%mod,add(a[i],l[i]); printf("%d\n",ans); }