URAL 1003,1004

1003:

并查集在处理矛盾关系的应用,讲的比较好的题解

#include <map>
#include <set>
#include <list>
#include <queue>
#include <stack>
#include <cmath>
#include <ctime>
#include <vector>
#include <bitset>
#include <cstdio>
#include <string>
#include <numeric>
#include <cstring>
#include <cstdlib>
#include <iostream>
#include <algorithm>
#include <functional>
using namespace std;
typedef long long  ll;
typedef unsigned long long ull;

int dx[4]={-1,1,0,0};
int dy[4]={0,0,-1,1};//up down left right
bool inmap(int x,int y,int n,int m){if(x<1||x>n||y<1||y>m)return false;return true;}
int hashmap(int x,int y,int m){return (x-1)*m+y;}

#define eps 1e-8
#define inf 0x7fffffff
#define debug puts("BUG")
#define lson l,m,rt<<1
#define rson m+1,r,rt<<1|1
#define read freopen("in.txt","r",stdin)
#define write freopen("out.txt","w",stdout)
#define N 11111

map<int,int>mp;
struct node
{
    int l,r;
    char c;
}nd[N>>1];
int fa[N<<1];
int find(int x)
{
    if (fa[x]!=x)
        fa[x] = find(fa[x]);
    return fa[x];
}

int gao(int m,int cnt)
{
    for (int i = 0; i < m; ++i)
    {
        int l = mp[nd[i].l-1], r= mp[nd[i].r];
        char c = nd[i].c;
        int f1 = find(l), f2 = find(r), f3 = find(l+cnt), f4 = find(r+cnt);
        if (c == 'e')
        {
            if (f1 == f4 && f2 == f3)
                return i;
            fa[f1] = f2;
            fa[f3] = f4;
        }
        else
        {
            if (f1 == f2)
                return i;
            fa[f1] = f4;
            fa[f2] = f3;
        }
    }
    return m;
}
int main()
{
    //read;
    int n,m;
    while (~scanf("%d",&n))
    {
        if (n == -1) break;
        scanf("%d",&m);
        mp.clear();
        int l, r, cnt = 0;
        char str[11];
        for (int i = 0; i < m; ++i)
        {
            scanf("%d%d%s",&l,&r,str);
            nd[i].l = l, nd[i].r = r;
            nd[i].c = str[0];
            if (mp.find(l-1) == mp.end())
                mp[l-1] = cnt++;
            if (mp.find(r) == mp.end())
                mp[r] = cnt++;
        }
        for (int i = 0; i < 2*cnt; ++i)
            fa[i] = i;
        int ans = gao(m,cnt);
        printf("%d\n", ans);
    }
    return 0;
}

 

1004:

能够加深对floyd理解的好题,当然还有另外的做法

#include <map>
#include <set>
#include <list>
#include <queue>
#include <stack>
#include <cmath>
#include <ctime>
#include <vector>
#include <bitset>
#include <cstdio>
#include <string>
#include <numeric>
#include <cstring>
#include <cstdlib>
#include <iostream>
#include <algorithm>
#include <functional>
using namespace std;
typedef long long  ll;
typedef unsigned long long ull;

int dx[4]={-1,1,0,0};
int dy[4]={0,0,-1,1};//up down left right
bool inmap(int x,int y,int n,int m){if(x<1||x>n||y<1||y>m)return false;return true;}
int hashmap(int x,int y,int m){return (x-1)*m+y;}

#define eps 1e-8
#define inf 0x7ffffff
#define debug puts("BUG")
#define lson l,m,rt<<1
#define rson m+1,r,rt<<1|1
#define read freopen("in.txt","r",stdin)
#define write freopen("out.txt","w",stdout)
#define N 155
int mp[N][N];
int dis[N][N];
int nxt[N][N];
stack<int>st;
int floyd(int n)
{
    int ans = inf;
    for (int k = 1; k <= n; ++k)
    {
        for (int i = 1; i < k; ++i)
            for (int j = i+1; j < k; ++j)
            {
                if (ans > dis[i][j] + mp[k][i] + mp[j][k])
                {
                    ans = dis[i][j] + mp[k][i] + mp[j][k];
                    while (!st.empty())
                        st.pop();
                    for (int t = i; t != j; t = nxt[t][j])
                        st.push(t);
                    st.push(j);
                    st.push(k);
                }
            }
        for (int i = 1; i <= n; ++i)
            for (int j = 1; j <= n; ++j)
            {
                if (dis[i][k] == inf || dis[k][j] == inf)
                    continue;
                if (dis[i][k] + dis[k][j] < dis[i][j])
                {
                    dis[i][j] = dis[i][k] + dis[k][j];
                    nxt[i][j] = nxt[i][k];
                }
            }
    }
    return ans;
}
int main()
{
    //read;
    int n,m;
    while (~scanf("%d",&n))
    {
        if (n == -1)break;
        scanf("%d",&m);
        for (int i = 1; i <= n; ++i)
            for (int j = 1; j <= n; ++j)
            {
                dis[i][j] = mp[i][j] = inf;
                nxt[i][j] = j;
            }
        int u,v,c;
        for (int i = 0; i < m; ++i)
        {
            scanf("%d%d%d",&u, &v, &c);
            if (mp[u][v] > c)
                mp[u][v] = mp[v][u] = dis[u][v] = dis[v][u] = c;
        }
        int ans = floyd(n);
        //printf("%d\n",ans);
        if (ans == inf)
            puts("No solution.");
        else
        {
            bool f = false;
            while (!st.empty())
            {
                if (f) printf(" ");
                else f = true;
                printf("%d",st.top());
                st.pop();
            }puts("");
        }
    }
    return 0;
}
posted @ 2015-09-15 11:48  McFlurry  阅读(142)  评论(0编辑  收藏  举报