P5149 会议座位

题目

会议座位

思路

最近看了看Trie数组,这个东西其实还蛮快的,就是容易爆内存V_V,然后再打一个求逆序对的板子就好了。

代码

注意开long long!

#include <bits/stdc++.h>
using namespace std;
const int N = 5 * 1e5 + 10;
int son[N][60], cnt[N], idx;
string tcher[N], tmp[N];

void insert(string s, int k) {
	int pos = 0;
	for (int i = 0; s[i]; ++i) {
		int t = s[i] - 'A';
		if (!son[pos][t])
			son[pos][t] = ++idx;
		pos = son[pos][t];
	}
	cnt[pos] = k;//记录下当前的位置
}

int query(string s) {
	int pos = 0;
	for (int i = 0; s[i]; ++ i) {
		int t = s[i] - 'A';
		if (!son[pos][t])
			return -1;
		pos = son[pos][t];
	}
	return cnt[pos];
}

long long merge_sort(int l, int r) {
	if (l >= r)
		return 0;
	long long res = 0;
	int mid = (l + r) >> 1;
	res = merge_sort(l, mid) + merge_sort(mid + 1, r);
	int k = 0, i = l, j = mid + 1;
	while (i <= mid and j <= r) {
		if (query(tcher[i]) <= query(tcher[j]))
			tmp[k++] = tcher[i++];
		else {
			tmp[k++] = tcher[j++];
			res += mid - i + 1;
		}
	}
	while (i <= mid)
		tmp[k++] = tcher[i++];
	while (j <= r)
		tmp[k++] = tcher[j++];
	for (int i = l, j = 0; i <= r; ++i, ++j)
		tcher[i] = tmp[j];
	return res;
}

int main() {
	cin.tie(0);
	ios::sync_with_stdio(false);
	int n;
	cin >> n;
	for (int i = 0; i < n ; ++ i) {
		string temp;
		cin >> temp;
		insert(temp, i);
		//temp是插入的名字 i是对应的编号
	}
	for (int i = 0; i < n; ++ i) {
		cin >> tcher[i];
	}
	cout << merge_sort(0, n - 1);
}
posted @ 2022-02-02 08:18  一袍清酒付l  阅读(29)  评论(0编辑  收藏  举报