CF731D.80-th Level Archeology(暴力)

爲什麼這麼水一道題沒人寫呢qwq
傳承cy的水博客精神(霧
傳送門RuA!

題意

給你一堆字符串(其實是數組?)對每個字符(數)+x+x(超過cc就從頭開始)
輸出任意一個使最後的字符串們字典序非遞減的xx就好啦!

Solution

要滿足整體字典序非遞減,那不就是前一個的字典序一定要小於等於當前的字典序咩?
發現兩個字符串的相對順序不會變所以只要找到相鄰兩個第一個不同的位置(或者說某一個先沒有了)
這樣我們就可以使前一個字母小於後一個字母所需要的xx範圍
於是得到nn個及以下的區間,最終取一個交集就好惹

(取交集用差分實現?
再隨便輸一個滿足的答案。。。)

Code

#include <cstdio>
#include <iostream>
#include <vector>
#define N 1000010

using namespace std;
int l[N], neq[N];
vector<int> p[N];

inline int read() {
	char ch = getchar();
	int x = 0;
	while (!isdigit(ch)) ch = getchar();
	while (isdigit(ch)) {
		x = (x << 1) + (x << 3) + (ch ^ 48);
		ch = getchar();
	}
	return x;
}

int main() {
	int n = read(), c = read();
	for (int i = 1; i <= n; ++i) {
		l[i] = read();
		for (int j = 1; j <= l[i]; ++j) {
			p[i].push_back(read());
		}
	}
	for (int i = 2; i <= n; ++i) {
		int now = 0;
		while (1) {
			if (now >= l[i - 1]) break;//後面比前面長,前面的串是後面這個串的某個前綴,所以一定滿足
			if (now >= l[i]) {//前面比後面長,後面的串是前面這個串的某個前綴,所以一定布星
				puts("-1");
				return 0;
			}
			if (p[i - 1][now] > p[i][now]) {//前面的比後面的來得大,前面得輪迴而後面不能。
				neq[0]++;
				neq[c - p[i - 1][now] + 1]--;
				neq[c - p[i][now] + 1]++;
				neq[c]--;
				break;
			}
			if (p[i - 1][now] < p[i][now]) {//前面的比後面的來得小,前面和後面一起輪迴或一起不輪迴。
				neq[c - p[i][now] + 1]++;
				neq[c - p[i - 1][now] + 1]--;
				break;
			}
			now++;
		}
	}
	for (int i = 0; i < c; ++i) {
		if (i) neq[i] += neq[i - 1];
		if (!neq[i]) {
			printf("%d\n", i);
			return 0;
		}
	}
	puts("-1");
	return 0;
}
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章