传送门


\(N \leq 20\)很小诶

一个暴力的思路是枚举行的翻转状态然后在列上贪心

复杂度为\(O(2^NM)\)显然过不去

考虑到可能有若干列的初始状态是一样的,那么在任意反转之后他们贪心的策略肯定是相同的

考虑状压,设\(f_i\)表示初始状态为\(i\)的列的个数,\(g_i\)表示经过行反转,某一列到达\(i\)状态时,这一列留下的最少的\(1\)的可能个数,\(h_i\)表示行翻转状态为\(i\)时的答案

那么\(h_i = \sum\limits_{j\ xor\ k = i}f_jg_k\),是一个异或卷积的形式,FWT即可。

#include<bits/stdc++.h>
using namespace std;

long long cnt1[1 << 20] , mn[1 << 20] , times[1 << 20] , ans[1 << 20] , num[100007] , N , M;

void FWT_xor(long long* arr , int type){
    for(int i = 1 ; i < 1 << N ; i <<= 1)
        for(int j = 0 ; j < 1 << N ; j += (i << 1))
            for(int k = 0 ; k < i ; ++k){
                long long x = arr[j + k] , y = arr[i + j + k];
                arr[j + k] = x + y;
                arr[i + j + k] = x - y;
                if(type == -1){
                    arr[j + k] >>= 1;
                    arr[i + j + k] >>= 1;
                }
            }
}

inline char getc(){
    char c = getchar();
    while(!isdigit(c))
        c = getchar();
    return c;
}

int main(){
    cin >> N >> M;
    for(int i = 1 ; i <= N ; ++i)
        for(int j = 1 ; j <= M ; ++j)
            num[j] = (num[j] << 1) + getc() - 48;
    for(int i = 1 ; i <= M ; ++i)
        ++times[num[i]];
    for(int i = 1 ; i < 1 << N ; ++i)
        cnt1[i] = cnt1[i - (i & -i)] + 1;
    for(int i = 1 ; i < 1 << N ; ++i)
        mn[i] = min(cnt1[i] , cnt1[((1 << N) - 1) ^ i]);
    FWT_xor(mn , 1);
    FWT_xor(times , 1);
    for(int i = 0 ; i < 1 << N ; ++i)
        ans[i] = mn[i] * times[i];
    FWT_xor(ans , -1);
    long long all = M * N;
    for(int i = 0 ; i < 1 << N ; ++i)
        all = min(all , ans[i]);
    cout << all;
    return 0;
}

CF662C Binary Table FWT的更多相关文章

  1. [CF662C Binary Table][状压+FWT]

    CF662C Binary Table 一道 FWT 的板子-比较难想就是了 有一个 \(n\) 行 \(m\) 列的表格,每个元素都是 \(0/1\),每次操作可以选择一行或一列,把 \(0/1\) ...

  2. CF662C Binary Table【FWT】

    CF662C Binary Table 题意: 给出一个\(n\times m\)的\(01\)矩阵,每次可以反转一行或者一列,问经过若干次反转之后,最少有多少个\(1\) \(n\le 20, m\ ...

  3. CROC 2016 - Final Round [Private, For Onsite Finalists Only] C. Binary Table FWT

    C. Binary Table 题目连接: http://codeforces.com/problemset/problem/662/C Description You are given a tab ...

  4. CF662C Binary Table 【状压 + FWT】

    题目链接 CF662C 题解 行比较少,容易想到将每一列的状态压缩 在行操作固定的情况下,容易发现每一列的操作就是翻转\(0\)和\(1\),要取最小方案,方案唯一 所以我们只需求出每一种操作的答案 ...

  5. CF662C Binary Table 枚举 FWT

    题面 洛谷题面 (虽然洛谷最近有点慢) 题解 观察到行列的数据范围相差悬殊,而且行的数量仅有20,完全可以支持枚举,因此我们考虑枚举哪些行会翻转. 对于第i列,我们将它代表的01串提取出来,表示为\( ...

  6. CF662C Binary Table (FWT板题)

    复习了一发FWT,发现还挺简单的... 没时间写了,就放一个博客吧:Great_Influence 的博客 注意这一句ans[i]=∑j⊗k=i​f[j]∗dp[k]ans[i]= ∑_{j⊗k=i} ...

  7. CF662C Binary Table (快速沃尔什变换FWT)

    题面 题解 我们会发现,如果单独的一列或一行,它的答案是O1确定的,如果确定了每一行是否变换,那么最后的答案也就简单了许多, 如果确定了行的变换状压下来是x(即x的i位表示第i行是否变换,理解就行), ...

  8. [CF662C] Binary Table(FWT)

    题意: https://www.cnblogs.com/cjyyb/p/9065801.html 题解:

  9. CodeForces - 662C Binary Table (FWT)

    题意:给一个N*M的0-1矩阵,可以进行若干次操作,每次操作将一行或一列的0和1反转,求最后能得到的最少的1的个数. 分析:本题可用FWT求解. 因为其0-1反转的特殊性且\(N\leq20\),将每 ...

随机推荐

  1. Core Animation-2:寄宿图

    #寄宿图 >图片胜过千言万语,界面抵得上千图片  ——Ben Shneiderman 我们在第一章『图层树』中介绍了CALayer类并创建了一个简单的有蓝色背景的图层.背景颜色还好啦,但是如果它 ...

  2. mysql的varchar字段可以存储多少个中文字符

    创建数据库,并创建一张表mytb进行测试 ******************************************************************************* ...

  3. nodejs在spawn中执行npm报错 [Error: spawn ENOENT]” errors

    描述: 上代码 var ps = require('child_process').spawn("npm", ['install'], { stdio: 'inherit', cw ...

  4. cx_Oracle读取Oracle数据库中文乱码问题解决

    在使用cx_Oracle模块读取Oracle数据库中的中文记录时,返回值皆为?,后google得此佳文,遂问题得以解决,特此记之. Oracle数据库版本是10g,字符集是AL32UTF8. 编写的p ...

  5. table表格(笔记)

    <table class="table table-hover2 pick_carTable"> <thead> <tr class="bl ...

  6. 使用vue的v-for生成table , 给table加上序号

    现在有一个使用mybatis的分页插件生成的table,table中数据是通过vue获得的 , 前台显示使用<tr v-for="item in items"> 后台v ...

  7. java 代码说明制作讲解

    命令格式及介绍 javadoc -d 文档存放目录 -author -version 源文件名.java 这条命令编译一个名为"源文件名.java"的 java 源文件,并将生成的 ...

  8. 【转载】Linux 内存管理机制

    在Linux中经常发现空闲内存很少,似乎所有的内存都被系统占用了,表面感觉是内存不够用了,其实不然.这是Linux内存管理的一个优秀特性,主要特点是,无论物理内存有多大,Linux 都将其充份利用,将 ...

  9. 详解JavaScript中void语句的使用

    void是在JavaScript中的一个重要的关键字可被用作其单操作数之前出现一元运算符,其可以是任何类型. 此运算符指定不需要返回值,进行计算的表达式.它的语法可能是下列之一: <script ...

  10. 控件_CheckBox(多选按钮)

    import android.os.Bundle; import android.app.Activity; import android.widget.CheckBox; import androi ...