二进制枚举

问题 A: 恋爱纪念日

#include <bits/stdc++.h>
using namespace std;
int days[13] = {
    0, 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31
};
bool isLeap(int y) {
    return (y % 400 == 0) || (y % 4 == 0 && y % 100);
}
int main(int argc, char *argv[]) {
    // ios::sync_with_stdio(false), cin.tie(0), cout.tie(0);
    int y, m, d, k;
    cin >> y >> m >> d >> k;
    int cnt = 0;
    for (int i = 1; i <= k; ++i) {
        if (isLeap(y)) days[2] = 29; // 如果是闰年那么对应数组天数变成29
        ++d;
        // 这一个月已经超过了, 往下一个月走, 天数变回1
        if (d > days[m]) { ++m; d = 1; }
        // 这一年已经超过了, 往下一年走, 月份变回1
        if (m > 12) { ++y; m = 1; }
        days[2] = 28; // 重置回28
    }
    printf("%04d-%02d-%02d\n", y, m, d);
    system("pause");
    return 0;
}

问题 B: 蒜头君的生日

#include <bits/stdc++.h>
using namespace std;
int larsen(int y, int m, int d) {
    if (m == 1 || m == 2) m += 12, --y;
    return (d + 2 * m + 3 * (m + 1) / 5 + y + y / 4 - y / 100 + y / 400 + 1) % 7;
}
string s[8] = {
    "Monday", "Tuesday", "Wednesday", "Thursday", "Friday", "Saturday", "Sunday"
};
int main(int argc, char *argv[]) {
    // ios::sync_with_stdio(false), cin.tie(0), cout.tie(0);
    int y, m, d;
    cin >> y >> m >> d;
    cout << s[larsen(y, m, d)] << '\n';
    // system("pause");
    return 0;
}

问题 C: 得到整数 X

#include <bits/stdc++.h>
using namespace std;
const int MAXN = 20 + 5;
int a[MAXN];
int main(int argc, char *argv[]) {
    // ios::sync_with_stdio(false), cin.tie(0), cout.tie(0);
    int n, X;
    cin >> n >> X;
    for (int i = 0; i < n; ++i) cin >> a[i];
    int res = 0;
    for (int state = 0; state < (1 << n); ++state) {
        int sum = 0;
        for (int mask = 0; mask < n; ++mask) {
            if (state & (1 << mask)) {
                sum += a[mask];
            }
        }
        if (sum == X) ++res;
    }
    cout << res << '\n';
    // system("pause");
    return 0;
}

问题 D: 节假日

#include <bits/stdc++.h>
using namespace std;
const int MAXN = 1e3 + 5;
int days[13] = {
    0, 31, 28, 31, 30, 31, 30, 31, 31, 30, 31, 30, 31
};
bool isLeap(int y) {
    return (y % 400 == 0) || (y % 4 == 0 && y % 100);
}
int a[MAXN];
bool vis[MAXN][MAXN]; // vis[i][j]: i月j日是否放假
int main(int argc, char *argv[]) {
    // ios::sync_with_stdio(false), cin.tie(0), cout.tie(0);
    // 标记阳历节假日
    vis[1][1] = vis[5][1] = vis[12][25] = true;
    vis[10][1] = vis[10][2] = vis[10][3] = true;
    int y;
    cin >> y;
    if (isLeap(y)) days[2] = 29;
    for (int i = 1; i <= 4; ++i) {
        int m, d;
        cin >>  m >> d;
        vis[m][d] = true;
        if (i == 1) { // 如果是春节需要特殊判断
            if (d + 1 > days[m]) vis[m + 1][1] = vis[m + 1][2] = true;
            else if (d + 2 > days[m]) vis[m][d + 1] = vis[m + 1][1] = true;
            else vis[m][d + 1] = vis[m][d + 2] = true;
        }
    }
    int k;
    cin >> k;
    int res = 0;
    for (int m = 1; m <= 12; ++m) {
        for (int d = 1; d <= days[m]; ++d) {
            // 如果是双休日或者节假日那么答案+1
            if (k >= 6 || vis[m][d]) ++res;
            if (++k > 7) k = 1;
        }
    }
    cout << res << '\n';
    // system("pause");
    return 0;
}

问题 E: islands 打炉石传说

#include <bits/stdc++.h>
using namespace std;
const int MAXN = 10 + 5;
struct Node {
    int cost, d, w;
} a[MAXN];
int main(int argc, char *argv[]) {
    // ios::sync_with_stdio(false), cin.tie(0), cout.tie(0);
    int n;
    cin >> n;
    for (int i = 0; i < n; ++i) {
        cin >> a[i].cost >> a[i].d >> a[i].w;
    }
    int res = 0;
    for (int state = 0; state < (1 << n); ++state) {
        bool f = false; // 标记有没有召唤随从
        int sum = 0, cost = 0; // sum记录攻击力, cost记录费用
        for (int mask = 0; mask < n; ++mask) {
            if (state & (1 << mask)) {
                if (a[mask].d == 0) f = true;
                sum += a[mask].w;
                cost += a[mask].cost;
            }
        }
        // 如果满足费用小于等于10并且至少选择了一个随从
        if (cost <= 10 && f) res = max(res, sum);
    }
    cout << res << '\n';
    system("pause");
    return 0;
}

问题 F: 幼儿园买玩具

#include <bits/stdc++.h>
using namespace std;
const int MAXN = 1e2 + 5;
int a[MAXN];
int main(int argc, char *argv[]) {
    // ios::sync_with_stdio(false), cin.tie(0), cout.tie(0);
    int n, m, k;
    cin >> n >> m >> k;
    for (int i = 1; i <= n; ++i) {
        int t;
        cin >> t;
        while (t--) {
            int x;
            cin >> x;
            a[i] |= 1 << (x - 1);
            // 将每个小朋友需要的玩具用二进制保存
            // 比如某个小朋友需要1和2那么a[i]就为00011
        }
        // bitset<5> bit(a[i]);
        // cout << bit << '\n';
    }
    int res = 0;
    for (int state = 0; state < (1 << k); ++state) {
        int cnt = 0;
        for (int mask = 0; mask < k; ++mask) {
            if (state & (1 << mask)) {
                ++cnt;
            }
        }
        // bitset<5> bit(state);
        // cout << bit << ' ' << cnt << '\n';
        if (cnt > m) continue;
        int sum = 0;
        for (int i = 1; i <= n; ++i) {
            // 因为位运算优先级较低所以要加上括号
            // 如果我买了的东西为1,3,4那么state就为01101
            // 假设有一个小朋友的状态为01001
            // 01101 & 
            // 01001 = 
            // 01001表示我买了的东西包括了小朋友需要的东西
            if ((state & a[i]) == a[i]) {
                ++sum;
            }
        }
        res = max(res, sum);
    }
    cout << res << '\n';
    system("pause");
    return 0;
}

问题 G: 十进制转换成二进制,求1的个数

#include <bits/stdc++.h>
using namespace std;
// 可以用ppt上的方法也可以枚举每一位复杂度接近
int main(int argc, char *argv[]) {
    // ios::sync_with_stdio(false), cin.tie(0), cout.tie(0);
    int T;
    cin >> T;
    while (T--) { 
        int x;
        cin >> x;
        int res = 0;
        // 类似打印十进制整数每一位
        // 比如9的二进制01001
        // 01001 >> 1 = 0100
        while (x) {
            res += x & 1; // 每次取出当前x的最后一位
            x >>= 1; // x的二进制不断左移直到为0
        }
        cout << res << '\n';
    }
    // system("pause");
    return 0;
}

问题 H: 十进制转成R进制

#include <bits/stdc++.h>
using namespace std;
string decToR(int n, int R) {
    bool sgn = n < 0; // 如果n小于0的话最后还要加上负号
    n = abs(n);
    string s, dic = "0123456789ABCDEF";
    while (n) {
        s += dic[n % R];
        n /= R;
    }
    if (sgn) s += '-';
    reverse(s.begin(), s.end());
    return s;
}
int main(int argc, char *argv[]) {
    // ios::sync_with_stdio(false), cin.tie(0), cout.tie(0);
    int n, R;
    while (cin >> n >> R) {
        // 注意特判0
        if (n == 0) cout << 0 << '\n'; 
        else cout << decToR(n, R) << '\n';
    }
    system("pause");
    return 0;
}
posted @ 2021-07-30 15:19  stler  阅读(104)  评论(0)    收藏  举报