首页 > 其他分享 >AT_arc126_d [ARC126D] Pure Straight 题解

AT_arc126_d [ARC126D] Pure Straight 题解

时间:2022-11-21 15:57:03浏览次数:86  
标签:ch Part 题解 Straight 状压 arc126 集合 dp

又来给 do_while_true 大佬交作业了,所以本篇题解仅仅是对 该篇题解 进行补充说明的。

本篇题解适用于像我这样的小萌新,那篇题解适合大佬食用。

Part 1:

为什么我们要用状压dp?

因为题解里面写了要用。

因为我们要进行对答案集合内的情况取最小值的操作,可以使用dp。并且 \(K \le 16\) 但 \(N \le 200\)。所以肯定是使用状压dp或者倍增优化dp。又发现是对一个集合里面的数进行的操作,且 \(2^K\) 的数组能开下,所以应该是状压dp。

Part 2:

状态的设计和转移。

跟着题解设计就行。

我们设 \(f_S\) 表示已经将 \(S\) 这个集合里的数字将题目要求的顺序排好的代价。我们插入一个新的数,她既可能去前面作为前面的排列中的一个数,也有可能去后面作为后面的排列中的这个数。对于集合整体,既可以将在这个集合里的数汇总起来,也可以将不在这个集合的数交换出去。

综上所述,我们可以得到这样的式子:

\(\forall x \notin S,f(S | (1 << x) = min\{f(S | (1 << x)),f(S) + popcount(s \& (~((1 << x) - 1)))\}\)

\(f(S) = min\{popcount(S),k - popcount(S)\}\)

Part 3:

上代码!!!!

点击查看代码
#include <bits/stdc++.h>

namespace hello_world_djh {
    template <typename T>
    T read() {
        T x = 0, f = 1;
        char ch = getchar();
        for (; ch < '0' || ch > '9'; ch = getchar())
            if (ch == '-')
                f = ~f + 1;
        for (; ch >= '0' && ch <= '9'; ch = getchar())
            x = (x << 3) + (x << 1) + (ch ^ '0');
        return x * f;
    }

    const int N = 210, K = 16, INF = 0x3f3f3f3f;
    int n = read<int>(), k = read<int>();
    int f[(1 << K) + 10];
    #define sum __builtin_popcount

    int main() {
        for (int i = 1; i <= (1 << k) - 1; i++)
            f[i] = INF;
        for (int i = 1; i <= n; i++) {
            int x = read<int>() - 1;
            for (int j = (1 << k) - 1; ~j; j--)
                if (f[j] != INF) {
                    if (!(j & (1 << x)))
                        f[j | (1 << x)] = std::min(f[j | (1 << x)], f[j] + sum(j & (~((1 << x) - 1))));
                    f[j] += std::min(sum(j), k - sum(j));
                }
        }
        printf("%d\n", f[(1 << k) - 1]);
        return 0;
    }
};

int main() {
    hello_world_djh::main();
    return 0;
}

标签:ch,Part,题解,Straight,状压,arc126,集合,dp
From: https://www.cnblogs.com/hello-world-djh/p/solution-at-arc126-d.html

相关文章

  • K8S kube-scheduler-master CreateContainerError 问题解决及思路
    错误信息1:kubectlgetpods  发现pod状态一直在runing-error-CrashLoopBackOff-循环解决方法:1,查看日志。kubectllogspodsweb-674477549d-zx8gmkubectldescri......
  • Python字符串的encode与decode研究心得乱码问题解决方法(转)
    ​​Python字符串的encode与decode研究心得乱码问题解决方法(转)​​为什么会报错“UnicodeEncodeError:'ascii'codeccan'tencodecharactersinposition0-1:o......
  • ABC278 整合题解
    AA题,送分题。link。思路数据范围很小,其实直接模拟也是可以通过的。不过我们很容易想到\(O(n)\)的算法。对于前\(k\)个数,不输出,其他数正常输出。然后再在末尾......
  • ABC278F 题解
    前言题目传送门!或许更好的阅读体验?博弈论,状压,记忆化搜索。思路看到很小的\(n\),容易联想到状压、搜索。本题就是状压加搜索。设状态\(x\)的每一位表示:如果第\(i\)......
  • [ARC152D] Halftree题解
    很好的一道题,即使是我这种菜鸡也感到心潮澎湃。直觉有余,证明不足。思路有余,推导不足。无论是什么比赛,对拍都是最有效的查错方式。本篇题解里的所有图片采用gra......
  • ABC278D 题解
    前言题目传送门!更好的阅读体验?难度加强版:P1253。思路很容易想到线段树。维护\(cov_i\)表示覆盖的懒标记。单点加与单点查都非常简单。全局覆盖只需要给每一层都打......
  • CF1383E Strange Operation 题解
    linkSolutionshaber题,但是又没有做出来。我们发现这个变化相当于可以任意删掉\(0\),\(1\)的话只有与\(1\)相邻的时候可以删掉。那么相当于我们可以把一段包含\(1\)......
  • [题解] Uoj Easy Round 11
    A使用动态规划,\(f_{i,j}\)代表竖着的前\(i\)个,第\(i\)个被第\(j\)个横着的挡住的方案数,当然前提是有\(l_j\gei\),否则\(f_{i,j}=0\)。转移就是做一遍前缀和。考......
  • ABC245G题解
    似乎是经典套路?先不考虑颜色限制,那么就直接把\(l\)个关键点当作起点跑多源最短路就行了。现在考虑颜色限制,有一种暴力的想法是枚举所有颜色,只把这种颜色的点当作起点,然......
  • Codeforces 1740 F Conditional Mix 题解
    题目链接对于任意一个multiset,我们都把它的元素从大到小排序来观察。发现一个multiset合法有个必要条件:对于每个i,multiset中最大的i个元素之和不能超过\(lim_i\),如果令\(c......