POJ--1386--Play on Words【判断有向图欧拉通路、欧拉回路】

题目要求通过n个单词首尾字母相连形成密码,如果能形成一个完整的路径则门可开启。有向图欧拉通路的充要条件是基图连通且所有顶点的出度等于入度,或两个顶点的出入度差为±1。欧拉回路的充要条件是所有顶点出入度相等。解决方法是将单词转化为有向图,然后检查图的连通性及顶点出入度,以确定是否存在欧拉通路或回路。
摘要由CSDN通过智能技术生成

链接:http://poj.org/problem?id=1386

题意:要开启一扇门,n个单词是密码,n个单词中,如果一个单词的首字母和前一个单词的尾字母相同,并且每个单词都能这么连起来且只用一次,则门可以开启,否则不能开启,现给出单词,判断门是否可以开。


有向图欧拉通路充要条件:D为有向图,D的基图连通,并且所有顶点的出度与入度都相等;或者除两个顶点外,其余顶点的出度与入度都相等,而这两个顶点中一个顶点的出度与入度之差为1,另一个顶点的出度与入度之差为-1。

有向图欧拉回路充要条件:当D的所有顶点的出、入度都相等时,D中存在有向欧拉回路。

思路:一个单词关键是首字母和尾字母,可以把首字母和尾字母看成顶点,这个单词看成这两个顶点间的边,这么建图,于是原题就变成了找这个图中是否存在欧拉通路或者欧拉回路。建完图之后只需要根据定理判断每个顶点的出度、入度以及图的连通性即可。


#include<cstring>
#include<string>
#include<fstream>
#include<iostream>
#include<iomanip>
#include<cstdio>
#include<cctype>
#include<algorithm>
#include<queue>
#include<map>
#include<set>
#include<vector>
#include<stack>
#include<ctime>
#include<cstdlib>
#include<functional>
#include<cmath>
using namespace std;
#define PI acos(-1.0)
#define MAXN 500100
#define eps 1e-7
#define INF 0x7FFFFFFF
#define LLINF 0x7FFFFFFFFFFFFFFF
#define seed 131
#define mod 1000000007
#define ll long long
#define ull unsigned ll
#define lson l,m,rt<<1
#define rson m+1,r,rt<<1|1

int du[30],vis[30],father[30];
int n,cnt;
char str[1010];
int Find(int x){
    int t = x;
    while(t!=father[t])
        t = father[t];
    int k = x;
    while(k!=t){
        int temp = father[k];
        father[k] = t;
        k = temp;
    }
    return t;
}
int main(){
    int t,i,j,l;
    scanf("%d",&t);
    while(t--){
        cnt = 0;
        memset(du,0,sizeof(du));
        memset(vis,0,sizeof(vis));
        for(i=0;i<30;i++)   father[i] = i;
        scanf("%d",&n);
        for(i=0;i<n;i++){
            scanf("%s",str);
            l = strlen(str);
            du[str[0]-'a']--;
            du[str[l-1]-'a']++;
            vis[str[0]-'a'] = 1;
            vis[str[l-1]-'a'] = 1;
            int aa = Find(str[0]-'a');
            int bb = Find(str[l-1]-'a');
            if(aa!=bb){
                if(aa<bb)   father[bb] = aa;
                else    father[aa] = bb;
            }
        }
        int flag1,flag2,flag3,flag;
        flag1 = flag2 = flag3 = flag = 0;
        for(i=0;i<30;i++){
            if(du[i]==0)    continue;
            else if(du[i]==-1)  flag1++;
            else if(du[i]==1)   flag2++;
            else    flag3 = 1;
        }
        if(!flag3&&flag1==1&&flag2==1)  flag = 1;
        else if(!flag1&&!flag2&&!flag3) flag = 1;
        else    flag = 0;
        if(flag){
            int tt = 0;
            for(i=0;i<26;i++){
                if(vis[i]&&father[i]==i){
                    tt++;
                }
            }
            if(tt>1)    flag = 0;
            if(flag)    puts("Ordering is possible.");
            else    puts("The door cannot be opened.");
        }
        else    puts("The door cannot be opened.");
    }
    return 0;
}




  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
package hamierton; import java.io.BufferedReader; import java.io.InputStreamReader; import java.util.ArrayList; import java.util.Random; public class EularCircuit { public EularCircuit() { } public static void main(String[] args) { // System.out.println("please input n:"); // BufferedReader br = new BufferedReader(new InputStreamReader(System.in)); int n = 4; try { // n = Integer.parseInt(br.readLine()); } catch (Exception ex) { return; } try { Graph g = new Graph(n); g.printg(); g.circuit(); } catch (Exception e) { System.out.println(e.toString()); e.printStackTrace(); return; } } } class Node { private static int count = 0; private String name; private ArrayList adjacencyList; private boolean visited =false; public Node() { name = "node " + count; adjacencyList = new ArrayList(); } public Node(String name) { this.name = name; adjacencyList = new ArrayList(); } public boolean isAllVisited() { for (int i = 0; i < adjacencyList.size(); i++) { SNode sn = (SNode) adjacencyList.get(i); if (sn.visited == false) { return false; } } return true; } public boolean isvisited(){ return visited; } public void setvisited(){ visited = true; } public int getAdjacencyCount() { return adjacencyList.size(); } public boolean contains(int i) { return this.adjacencyList.contains(new SNode(i)); } public void removeAdjacencyNode(int i) { this.adjacencyList.remove(new SNode(i)); } public void addAdjacencyNode(int i) { this.adjacencyList.add(new SNode(i)); } public SNode getAdjacencyNode(int i) { return (SNode) this.adjacencyList.get(i); } public SNode getAdjacencyNodeEX(int i_ref) { for (int i = 0; i < this.getAdjacencyCount(); i++) { if (getAdjacencyNode(i).index == i_ref) { return getAdjacencyNode(i); } } return null; } public String toString() { return this.name; } } class SNode { public boolean visited = false; public int index = 0; public SNode(int index) { this.index = index; } public boolean equals(Object o) { if (((SNode) o).index == this.index) { return true; } return false; } public String toString() { return "adjacency " + index; } } class Graph { private ArrayList nodeList; private ArrayList path; private int count; public Graph(int n) throws Exception { this.count = n; nodeList = new ArrayList(count); ginit(); } public void circuit() { path = new ArrayList(); int top = 0; int k = 0; path.add(new Integer(0)); while (true) { int i, j; i = top; ArrayList path1 = new ArrayList(); path1.add(new Integer(top)); while (true) { Node node = (Node) nodeList.get(i); for (j = 0; j < this.count; j++) { if (node.contains(j) && node.getAdjacencyNodeEX(j).visited == false) { path1.add(new Integer(j)); node.getAdjacencyNodeEX(j).visited = true; // ((Node) nodeList.get(j)).getAdjacencyNodeEX(i).visited = true; i = j; break; } } if (i == top) { break; } } path.remove(k); path.addAll(k, path1); k++; if (k >= path.size()) { break; } top = ((Integer) path.get(k)).intValue(); } for (int z = 0; z < path.size(); z++) { System.out.print(path.get(z).toString() + " "); } } private void ginit() { int i; for (i = 0; i < 4; i++) { nodeList.add(new Node("node" + i)); } ((Node)nodeList.get(0)).addAdjacencyNode(3); ((Node)nodeList.get(1)).addAdjacencyNode(0); ((Node)nodeList.get(2)).addAdjacencyNode(1); ((Node)nodeList.get(3)).addAdjacencyNode(2); // ((Node)nodeList.get(0)).addAdjacencyNode(3); // ((Node)nodeList.get(1)).addAdjacencyNode(0); // ((Node)nodeList.get(2)).addAdjacencyNode(1); // ((Node)nodeList.get(3)).addAdjacencyNode(2); // for (i = 0; i < n; i++) { // nodeList.add(new Node("node" + i)); // } // ArrayList linked = new ArrayList(); // linked.add(new Integer(0)); // Random rand = new Random(); // // for (i = 1; i < n; i++) { // int size = linked.size(); // // int top = ((Integer) (linked.get(size - 1))).intValue(); // Node node = (Node) (nodeList.get(top)); // // while (true) { // int randint = rand.nextInt(n); // if (randint == top) { // continue; // } // if (node.contains(randint)) { // continue; // } else { // if (!linked.contains(new Integer(randint))) { // linked.add(new Integer(randint)); // } else if (node.getAdjacencyCount() >= (linked.size() - 1 > 6 ? 6 // : linked.size() - 1)) { // continue; // } else { // i--; // } // node.addAdjacencyNode(randint); // Node randnode = (Node) nodeList.get(randint); // randnode.addAdjacencyNode(top); // break; // } // } // } // // for (i = 0; i < this.count - 1; i++) { // Node node = (Node) nodeList.get(i); // if (node.getAdjacencyCount() % 2 != 0) { // int j = 0; // for (j = i + 1; j < this.count; j++) { // Node nn = (Node) nodeList.get(j); // if (nn.getAdjacencyCount() % 2 != 0) { // if (node.contains(j)) { // // if (nn.getAdjacencyCount() != 1 // && node.getAdjacencyCount() != 1) { // node.removeAdjacencyNode(j); // nn.removeAdjacencyNode(i); // break; // } else { // continue; // } // } else { // // node.addAdjacencyNode(j); // nn.addAdjacencyNode(i); // break; // } // } // } // // if (j == this.count) { // int k; // Node nk = null; // for (k = i + 1; k < this.count; k++) { // // nk = (Node) nodeList.get(k); // if (nk.getAdjacencyCount() % 2 != 0) { // break; // } // } // int kk = k; // for (k = 0; k < i; k++) { // Node n1 = (Node) nodeList.get(k); // if (!n1.contains(kk) && !n1.contains(i)) { // n1.addAdjacencyNode(kk); // nk.addAdjacencyNode(k); // n1.addAdjacencyNode(i); // node.addAdjacencyNode(k); // break; // } // } // boolean retry = false; // // if (k == i) { // int vv; // for (vv = 0; vv < this.count; vv++) { // Node vn = (Node) nodeList.get(vv); // if (!vn.contains(i) && i != vv) { // vn.addAdjacencyNode(i); // node.addAdjacencyNode(vv); // retry = true; // break; // } // } // if (vv == count) { // for (vv = 0; vv < count; vv++) { // Node vnn = (Node) nodeList.get(vv); // if (vnn.getAdjacencyCount() > 1) { // vnn.removeAdjacencyNode(i); // node.removeAdjacencyNode(vv); // retry = true; // break; // } // } // } // } // if (retry) { // i = -1; // } // } // } // // } // return this.isEularG(); } public boolean isEularG() { boolean isEular = true; for (int i = 0; i < this.count; i++) { Node n = (Node) nodeList.get(i); if (n.getAdjacencyCount() % 2 != 0) { isEular = false; break; } } return isEular; } public void printg() { for (int i = 0; i < this.count; i++) { Node n = (Node) nodeList.get(i); System.out.print(n.toString() + " "); for (int j = 0; j < n.getAdjacencyCount(); j++) { System.out.print(n.getAdjacencyNode(j).toString() + " "); } System.out.println(); } } }
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值