bzoj 1770 [Usaco2009 Nov]lights 燈 meet in the middle

题面

题目传送门

解法

题解里都是高斯消元然后dfs,蒟蒻表示不会

直接分两半dfs即可

时间复杂度:\(O(2^{\frac{n}{2}})\)

代码

#include <bits/stdc++.h>
#define LL long long
#define N 110
using namespace std;
template <typename node> void chkmax(node &x, node y) {x = max(x, y);}
template <typename node> void chkmin(node &x, node y) {x = min(x, y);}
template <typename node> void read(node &x) {
    x = 0; int f = 1; char c = getchar();
    while (!isdigit(c)) {if (c == ‘-‘) f = -1; c = getchar();}
    while (isdigit(c)) x = x * 10 + c - ‘0‘, c = getchar(); x *= f;
}
int ans; LL s[N];
vector <int> e[N];
map <LL, int> h;
void dfs1(int x, int n, int sum, LL tmp) {
    if (x > n) {
        h[tmp] = sum;
        return;
    }
    dfs1(x + 1, n, sum + 1, tmp ^ s[x]);
    dfs1(x + 1, n, sum, tmp);
}
void dfs2(int x, int n, int sum, LL tmp) {
    if (x > n) {
        LL y = ((1ll << n) - 1) ^ tmp;
        if (h.count(y)) chkmin(ans, h[y] + sum);
        return;
    }
    dfs2(x + 1, n, sum + 1, tmp ^ s[x]);
    dfs2(x + 1, n, sum, tmp);
}
int main() {
    int n, m; read(n), read(m);
    for (int i = 1; i <= m; i++) {
        int x, y; read(x), read(y);
        s[x] |= 1ll << y - 1;
        s[y] |= 1ll << x - 1;
    }
    for (int i = 1; i <= n; i++) s[i] |= 1ll << i - 1;
    dfs1(1, n / 2, 0, 0);
    ans = INT_MAX; dfs2(n / 2 + 1, n, 0, 0);
    cout << ans << "\n";
    return 0;
}

原文地址:https://www.cnblogs.com/copperoxide/p/9476736.html

时间: 2024-10-08 18:46:01

bzoj 1770 [Usaco2009 Nov]lights 燈 meet in the middle的相关文章

BZOJ 1770: [Usaco2009 Nov]lights 燈

1770: [Usaco2009 Nov]lights 燈 Time Limit: 10 Sec  Memory Limit: 64 MBSubmit: 840  Solved: 397[Submit][Status][Discuss] Description 貝希和她的閨密們在她們的牛棚中玩遊戲.但是天不從人願,突然,牛棚的電源跳閘了,所有的燈都被關閉了.貝希是一個很膽小的女生,在伸手不見拇指的無盡的黑暗中,她感到驚恐,痛苦與絕望.她希望您能夠幫幫她,把所有的燈都給重新開起來!她才能繼續快樂地

BZOJ 1770: [Usaco2009 Nov]lights 燈( 高斯消元 )

高斯消元解xor方程组...暴搜自由元+最优性剪枝 ----------------------------------------------------------------------------- #include<cstdio> #include<cstring> #include<algorithm> #include<bitset> using namespace std; const int maxn = 49; int N, Id[max

BZOJ 1770 [Usaco2009 Nov]lights 燈 【高斯消元】

Description 貝希和她的閨密們在她們的牛棚中玩遊戲.但是天不從人願,突然,牛棚的電源跳閘了,所有的燈都被關閉了.貝希是一個很膽小的女生,在伸手不見拇指的無盡的黑暗中,她感到驚恐,痛苦與絕望.她希望您能夠幫幫她,把所有的燈都給重新開起來!她才能繼續快樂地跟她的閨密們繼續玩遊戲! 牛棚中一共有N(1 <= N <= 35)盞燈,編號為1到N.這些燈被置於一個非常複雜的網絡之中.有M(1 <= M <= 595)條很神奇的無向邊,每條邊連接兩盞燈. 每盞燈上面都帶有一個開關.當

【高斯消元】BZOJ 1770: [Usaco2009 Nov]lights 燈

Description 貝希和她的閨密們在她們的牛棚中玩遊戲.但是天不從人願,突然,牛棚的電源跳閘了,所有的燈都被關閉了.貝希是一個很膽小的女生,在伸手不見拇指的無盡的黑暗中,她感到驚恐,痛苦與絕望.她希望您能夠幫幫她,把所有的燈都給重新開起來!她才能繼續快樂地跟她的閨密們繼續玩遊戲! 牛棚中一共有N(1 <= N <= 35)盞燈,編號為1到N.這些燈被置於一個非常複雜的網絡之中.有M(1 <= M <= 595)條很神奇的無向邊,每條邊連接兩盞燈. 每盞燈上面都帶有一個開關.當

BZOJ 1770: [Usaco2009 Nov]lights 燈 [高斯消元XOR 搜索]

题意: 经典灯问题,求最少次数 本题数据不水,必须要暴搜自由元的取值啦 想了好久 然而我看到网上的程序都没有用记录now的做法,那样做遇到自由元应该可能会丢解吧...? 我的做法是把自由元保存下来,枚举的时候只枚举自由元 但这样没法最优性剪枝了 于是枚举的时候还是从n到1枚举,到i时如果i是主元这时候i的值已经可以算出来了,这样就可以最优性剪枝了 但注意主元i你不能用i这个方程,而要保存pivot[i]为i用了哪个方程 然后一个伪贪心策略是自由元先搜0 #include <iostream>

BZOJ1770 : [Usaco2009 Nov]lights 燈

设$f[i]$表示$i$点按下开关后会影响到的点的集合,用二进制表示. 不妨设$n$为偶数,令$m=\frac{n}{2}$,对于前一半暴力$2^m$搜索所有方案,用map维护每种集合的最小代价. 对于后一半暴力$2^m$搜索所有方案,在map中查询补集. 时间复杂度$O(n2^{\frac{n}{2}})$. #include<cstdio> #include<map> #define N 36 typedef long long ll; int n,m,i,x,y,ans=N,

bzoj:2018: [Usaco2009 Nov]农场技艺大赛

Description Input 第1行:10个空格分开的整数: N, a, b, c, d, e, f, g, h, M Output 第1行:满足总重量最轻,且用度之和最大的N头奶牛的总体重模M后的余数. Sample Input 2 0 1 5 55555555 0 1 0 55555555 55555555 Sample Output 51 HINT 样例说明:公式生成的体重和有用度分别为: 体重:5, 6, 9, 14, 21, 30 有用度:0, 1, 8, 27, 64, 125

BZOJ 2017: [Usaco2009 Nov]硬币游戏(A Coin Game)

题目链接:http://www.lydsy.com/JudgeOnline/problem.php?id=2017 参考题解:http://www.mamicode.com/info-detail-1582288.html 解:看的时候觉得是动归,然而不会设也不会列,看了半天别人的题解... 首先我们用f[i][j]来表示还剩下后i个硬币要取,上一步取了j个硬币,接下来的步骤中能获得的最大价值. 然后呢,假设在这一步是第一个人取,要取k个,k<=min(2*j,i),很显然,因为第二个人也会取最

[Usaco2009 Nov]lights(高斯消元)

luogu 点灯游戏应该很多人都在小时候頽过吧 反正我直到现在也不会 很明显一个灯最多只需要点一次 然后高斯消元 解完肯定剩自由元(就是那些全是0的行) 然后这些都爆搜 由于剩下的自由元不会太多 所以时间复杂度$O(能过)$ 以上 1 #include<cstdio> 2 #include<algorithm> 3 using std::swap; 4 const int N=40; 5 template<typename tp>void read(tp &kk