UVALive - 4294 Shuffle 映射+取反+最大区间覆盖
来源:互联网 发布:志鸿优化系列赢在高考 编辑:程序博客网 时间:2024/06/02 05:31
You are listening to your music collection using the shuffle function to keep the music surprising. You assume that the shuffle algorithm of your music player makes a random permutation of the songs in the playlist and plays the songs in that order until all songs have been played. Then it reshuffles and starts playing the list again.
You have a history of the songs that have been played. However, your record of the history of played songs is not complete, as you started recording songs at a certain point in time and a number of songs might already have been played. From this history, you want to know at how many different points in the future the next reshuffle might occur.
A potential future reshuffle position is valid if it divides the recorded history into intervals of lengths (the number of songs in the playlist) with the first and last interval possibly containing less than s songs and no interval contains a specific song more than once.
Input
On the first line there exists one positive number: the number of test cases, at most 100. After that per test case there exists:
• One line with two integers s and n (1 ≤ s, n ≤ 100000): the number of different songs in the playlist and the number of songs in the recorded playlist history.
• One line with n space separated integers, x1, x2, . . . , xn (1 ≤ xi ≤ s): the recorded playlist history.
Output
Per test case there exists:
• One line with the number of future positions the next reshuffle can be at. If the history couldnot be generated by the above mentioned algorithm, output ‘0’.
Sample Input
4
4 10
3 4 4 1 3 2 1 2 3 4
6 6
6 5 4 3 2 1
3 5
3 3 1 1 1
7 3
5 7 3
Sample Output
1
6
0
7
Source
UVALive - 4294
My Solution
题意:歌曲种数为s,记录的数量为n,然后给出这个n个记录,每s个歌会随机播放一遍,然后开始重新随机播放这s首歌,为未来可能在几个点进行一次新的循环。
映射+取反+最大区间覆盖
扫一遍数组,每次如果i - last[v[i]] < s,则点x必须是在这个区间里划分,然后新的循环会在kx之后出现,
所以把i和last[v[i]]映射到 [0, s) 里,
然后如果 (i % s) > (last[v[i]] % s) 则答案在区间[(last[v[i]] % s), (i % s))里,取反以后
是答案不可能在 [0, (last[v[i]] % s) ) 和[(i % s), s)里。
如果 (i % s) < (last[v[i]] % s) 则答案在区间 [0, (i % s)) 和[(last[v[i]] % s), s)里,取反以后
答案不可能在区间[(i % s), (last[v[i]] % s))里
然后跑一遍把所有的不可能区间搞出来,然后就是最大区间覆盖问题,ans = s - 最大区间覆盖
复杂度 略大于O(n) 远小于 O(nlogn)
#include <iostream>#include <cstdio>#include <cstring>#include <vector>#include <algorithm>using namespace std;typedef long long LL;const int maxn = 1e5 + 8;const int INF = 1e9 + 7;int v[maxn], last[maxn];struct interval{ int l, r; interval(int x, int y) : l(x), r(y) {}};vector<interval> val;inline bool cmp(const interval& a, const interval& b){ if(a.l != b.l) return a.l < b.l; else return a.r < b.r;}int main(){ #ifdef LOCAL freopen("h.txt", "r", stdin); //freopen("h.out", "w", stdout); #endif // LOCAL //ios::sync_with_stdio(false); cin.tie(0); int T, s, n, i, j, sz, ans; scanf("%d", &T); while(T--){ val.clear(); memset(last, -1, sizeof last); scanf("%d%d", &s, &n); for(i = 0; i < n; i++){ cin >> v[i]; if(last[v[i]] != -1){ if(i - last[v[i]] < s){ if((i % s) > (last[v[i]] % s)){ val.push_back(interval(0, (last[v[i]] % s))); val.push_back(interval((i % s), s)); } else{ val.push_back(interval((i % s), (last[v[i]] % s))); } } } last[v[i]] = i; } sort(val.begin(), val.end(), cmp); sz = val.size(); ans = s; for(i = 0; i < sz; i++){ if(i + 1 < sz && val[i].r >= val[i + 1].l) { val[i + 1].l = val[i].l; val[i].l = INF; val[i+1].r = max(val[i].r, val[i + 1].r); } else{ ans -= val[i].r - val[i].l; } } printf("%d\n", ans); } return 0;}
Thank you!
------from ProLights
- UVALive - 4294 Shuffle 映射+取反+最大区间覆盖
- UVALive - 4294 Shuffle
- 取小区间覆盖
- uvalive 2326 - Moving Tables(区间覆盖问题)
- UVALive 3510 Pixel Shuffle
- uvaLive 2387 - Gene Assembly 最大区间调度问题
- hdu 1050 Moving Tables(最大区间覆盖问题)
- uva 10535 - Shooter(几何+最大区间覆盖)
- 贪心法——区间的最大覆盖数
- hdu4293(最大无覆盖区间权值)
- UVALive 2930 Minimizing Maximizer(最小区间覆盖数 DP + 线段树优化)
- uvaLive 3222 Joke with Turtles 带权区间调度、覆盖问题 等价转换+线性动归
- 区间覆盖
- BSOJ1125:树Tree 树链剖分 单点修改 区间取反 区间查询
- 区间完全覆盖问题 &&区间均取最少2个点的问题
- 区间选点+区间覆盖
- hdu6103Kirinriki(第六场尺取法取区间最大)
- 取反
- 2016年个人总结社区版
- ubuntu上pycharm缺少libcupti.so
- 搜索看看? 搜索 User Defined Runtime Attributes
- skynet范例研究-服务端
- C++初步(3)
- UVALive - 4294 Shuffle 映射+取反+最大区间覆盖
- 2017年前思绪整理
- 九度 oj 题目1149:子串计算
- 源码安装PHP扩展mysqli
- 未完成呀
- 各种linux系统配置多IP方法整理
- LeetCode 167. Two Sum II - Input array is sorted
- 0121
- 2017年要学习的三个CSS新特性