zoukankan      html  css  js  c++  java
  • noip模拟赛 罪犯分组

    分析:看了题后没别的思路,感觉就是dp,普通dp的话状态和方程实在是不好设计,观察数据,发现N非常小,暗示了这道题要用状压dp来做.

          先枚举每个集合,再用O(n^2)的暴力看这个集合内有多少个冲突,如果冲突数量不大于k,那么就可以分成1个集合了,否则一定要分成多个集合,那么枚举它的子集j,状态转移方程就出来了:f[i] = min{f[j] + f[i ^ j]} j是i的子集.

    以后没思路要多往dp上面去想,还要注意看数据范围,有一个值特别小就很有可能是状压dp.

    #include <cstdio>
    #include <cstring>
    #include <iostream>
    #include <algorithm>
    
    using namespace std;
    
    const int inf = 0x7fffffff;
    int n, m, k,a[20][20],f[10000010];
    
    int main()
    {
        scanf("%d%d%d", &n, &m, &k);
        for (int i = 1; i < (1 << n); i++)
            f[i] = inf;
        for (int i = 1; i <= m; i++)
        {
            int x, y;
            scanf("%d%d", &x, &y);
            a[x][y] = a[y][x] = 1;
        }
        for (int i = 1; i < (1 << n); i++)
        {
            int cnt = 0;
            for (int j = 1; j <= n; j++)
                for (int l = j + 1; l <= n; l++)
                    if (a[j][l] && (i & (1 << (j - 1)) && (i & (1 << (l - 1)))))
                        cnt++;
            if (cnt <= k)
                f[i] = 1;
            else
            {
                for (int j = i; j; j = (j - 1) & i)
                    f[i] = min(f[i], f[j] + f[i ^ j]);
            }
        }
        printf("%d
    ", f[(1 << n) - 1]);
    
        return 0;
    }
  • 相关阅读:
    Mysql数据优化--DBA梳理珍藏篇
    Spring缓存注解@Cacheable
    Spring常用知识点
    谈一谈对MySQL InnoDB的认识及数据库事物处理的隔离级别
    MySQL主从复制的实现过程
    List 与 数组 互转
    位运算实现小正整数乘法
    最大的K个数
    Java 编码与字符(2)
    JSP工作原理
  • 原文地址:https://www.cnblogs.com/zbtrs/p/7581611.html
Copyright © 2011-2022 走看看