zoukankan      html  css  js  c++  java
  • [洛谷] AT2164 [AGC006C] Rabbit Exercise

    Description

    (Link)

    Solution

    一道好题,涉及到差分化简以及倍增求置换。

    注意到一次操作后,(a[i])的位置期望为(E(a[i])=frac{1}{2}(E(2a[i+1]-a[i])+E(2a[i-1]-a[i]))=E(a[i+1]+a[i-1]-a[i]))

    这么看不太好求。但对(a)差分后,发现一次这样的操作就是对差分数组(d)进行(swap(d[i],d[i+1]))

    那么就是对(d)进行(k)轮置换。注意到(k)很大,可以通过倍增优化,和快速幂类似。

    即我们记录两个数组(p)(q)(p)保存置换一轮后的结果,相当于快速幂的(base)。而(q)保存答案即可。

    Code

    #include <bits/stdc++.h>
    
    using namespace std;
    
    #define ll long long
    
    int n, m, x[100005], p[100005], q[100005], a[100005], cnt[100005];
    
    ll sum, k;
    
    int read()
    {
    	int x = 0, fl = 1; char ch = getchar();
    	while (ch < '0' || ch > '9') { if (ch == '-') fl = -1; ch = getchar();}
    	while (ch >= '0' && ch <= '9') {x = (x << 1) + (x << 3) + ch - '0'; ch = getchar();}
    	return x * fl;
    }
    
    int main()
    {
    	n = read();
    	for (int i = 1; i <= n; i ++ )
    	{
    		x[i] = read();
    		p[i] = q[i] = i;
    	}
    	m = read(); scanf("%lld", &k);
    	for (int i = 1; i <= m; i ++ )
    	{
    		a[i] = read();
    		swap(p[a[i]], p[a[i] + 1]);
    	}
    	while (k)
    	{
    //		printf("%lld
    ", k);
    		if (k & 1ll)
    		{
    			for (int i = 1; i <= n; i ++ )
    				cnt[i] = q[p[i]];
    			for (int i = 1; i <= n; i ++ )
    				q[i] = cnt[i];
    		}
    		for (int i = 1; i <= n; i ++ )
    			cnt[i] = p[p[i]];
    		for (int i = 1; i <= n; i ++ )
    			p[i] = cnt[i];
    		k >>= 1ll;
    	}
    	for (int i = 1; i <= n; i ++ )
    	{
    		sum += (ll)(x[q[i]] - x[q[i] - 1]);
    		printf("%.1lf
    ", (double)(sum));
    	}
    	return 0;
    }
    
  • 相关阅读:
    结合php ob函数理解缓冲机制
    php中的require-once
    PHP面试题基础问题
    Jquery显示与隐藏input默认值的实现代码
    win7下cmd常用命令
    采用cocos2d-x lua 的listview 实现pageview的翻页效果之上下翻页效果
    采用cocos2d-x lua 制作数字滚动效果样例
    luac++
    lua相关笔记
    cornerstone知识点
  • 原文地址:https://www.cnblogs.com/andysj/p/14435892.html
Copyright © 2011-2022 走看看