专栏文章
题解:P11934 [CrCPC 2024] 排序
P11934题解参与者 1已保存评论 0
文章操作
快速查看文章及其快照的属性,并进行相关操作。
- 当前评论
- 0 条
- 当前快照
- 1 份
- 快照标识符
- @miprv48b
- 此快照首次捕获于
- 2025/12/03 16:55 3 个月前
- 此快照最后确认于
- 2025/12/03 16:55 3 个月前
暴力枚举三个分割点跑 DFS 即可,考虑剪枝:定义两个衡量操作价值的数:。显然 应该尽量大, 应该尽量小。用这两个标准比对修改前后的序列剪枝。
CPPconst ll N = 20, MAX = 6;
ll n, a[N], ans = MAX, goal;
map<ll, bool> vis;
map<ll, ll> mem;
ll hash1() {
ll ret = 0;
rep(i, 1, n) ret = ret * 10 + a[i] - 1;
return ret;
}
void dfs(ll step) {
// cout << "dfs:step=" << step << ",status=";
//
// rep(i, 1, n) cout << a[i] << ' ';
//
// endl;
// pause;
ll tmp = hash1();
// cout << "tmp=" << tmp << '\n';
// pause;
if ((vis[tmp] and mem[tmp] <= step) or step >= ans)
return;
// cout << "signal!\n";
vis[tmp] = 1;
mem[tmp] = step;
if (tmp == goal) {
update(ans, step, min);
return;
}
ll v11 = 0, v12 = 0;
rep(i, 1, n - 1) {
if (a[i] + 1 == a[i + 1])
v11++;
else if (a[i] > a[i + 1])
v12++;
}
rep(i, 0, n) {
rep(j, i, n) {
rep(k, j, n) {
// cout << "status=";
//
// rep(i, 1, n) cout << a[i] << ' ';
//
// endl;
// pause;
// cout << i << ' ' << j << ' ' << k << '\n';
// pause;
vector<ll> new1;
new1.clear();
rep(l, j + 1, k) new1.pb(a[l]);
rep(l, 1, i) new1.pb(a[l]);
rep(l, k + 1, n) new1.pb(a[l]);
rep(l, i + 1, j) new1.pb(a[l]);
// cout << "size:" << new1.size() << '\n';
// pause;
// for (ll l : new1)
// cout << l << ' ';
//
// endl;
// pause;
ll v21 = 0, v22 = 0;
rep(l, 0, n - 2) {
if (new1[l] + 1 == new1[l + 1])
v21++;
else if (new1[l] > new1[l + 1])
v22++;
}
// cout << "v11=" << v11 << ",v12=" << v12 << ",v21=" << v21 << ",v22=" << v22 << '\n';
// pause;
if (v11 >= v21 or v22 > v12)
ctn;
// cout << "signal A\n";
ll _a[N];
cpy(_a, a);
rep(i, 1, n) a[i] = new1[i - 1];
dfs(step + 1);
cpy(a, _a);
}
}
}
}
int main() {
cin >> n;
rep(i, 1, n) cin >> a[i];
rep(i, 0, n - 1) goal = goal * 10 + i;
// cout << "goal=" << goal << '\n';
// pause;
dfs(0);
cout << ans;
}
相关推荐
评论
共 0 条评论,欢迎与作者交流。
正在加载评论...