ACM-ICPC(11/9)

今天看了一下黑书,感觉很刘汝佳,是他的风格,题目挺好的~~~

  • 枚举

P12翻硬币

二进制枚举每一列的情况2^9种。

在每一种情况下然后对于每一行就是翻与不翻的两种情况~~~

  • 贪心

P13钓鱼问题

POJ上有,之前做过,可以再优化一下。

首先枚举在哪里结束,然后剩下的时间就是用来钓鱼,每次选取当前最大的钓鱼,然后更新当前值(优先队列插入与弹出)

  • 递归

P20三色三角形

当查找失败的时候还是要回溯一下,看了一下网上的代码,发现好像我的是最短的~~~

#include <bits/stdc++.h>

using namespace std;

char str[1005];
vector<char> v;

map<int,int> mp;
int n;
bool flag[1005];
struct Ans {
    int a,b;
}ans[1005];

struct Node {
    char s;
    int pos;
};

int cnt;
bool solve(vector<Node> &v) {
    int len = v.size();
    if(len==3) {
        if(v[0].s!=v[1].s&&v[0].s!=v[2].s&&v[1].s!=v[2].s) {
            return true;
        }
        return false;
    }
    for(int i = 0; i < len; i++) {
        Node tmp  = v[(i+1)%len];
        if(v[i].s!=v[(i+1)%len].s&&v[i].s!=v[(i+2)%len].s&&v[(i+1)%len].s!=v[(i+2)%len].s) {
            ans[cnt].a = v[i].pos;
            ans[cnt++].b = v[(i + 2)%n].pos;
            auto it = v.begin() + (i+1)%n;
            v.erase(it);
            if(solve(v)==true)
                return true;
            cnt--;
            v.insert(it,tmp);
        }
    }
    return false;
}

vector<Node> strs;
int main()
{
    scanf("%d%s",&n,str);

    for(int i = 0; i < n; i++)
        strs.push_back((Node){str[i],i});

    if(!solve(strs)) {
        puts("0");
    }
    else {
        printf("%d
",cnt);
        for(int i = 0; i < cnt; i++)
            printf("%d %d
",ans[i].a+1,ans[i].b+1);

    }
    return 0;
}
View Code
原文地址:https://www.cnblogs.com/TreeDream/p/7812102.html