For the question & #160; see the Chinese translation below. each word can be considered as an edge connecting the first and last two letters & #160; then input m sides & #160; determine whether a directed Euler's path can be formed. the condition that a directed graph has an Euler's path is: & #160; 1. connected to the base graph of a directed graph. & amp; #160; 2. the outbound and inbound degrees of all vertices are equal & #160; or & #160; only two vertices with different inbound and outbound Degrees & #16
For the question, see Chinese translation below
Each word can be regarded as an edge connected by two letters at the beginning and end, and then m edge is entered to determine whether it can constitute a directed Euler's path.
Necessary and sufficient conditions for a directed graph to have Euler's path:
1. connected to the base graph of a directed graph;
2. the outbound and inbound degrees of all vertices are equal or only two vertices with unequal inbound and outbound degrees. The difference between the inbound and outbound degrees of these two vertices is-1 (starting point) one is 1 (endpoint ).
Determine whether the connection is an application and check the set
# Include
# Include
Using namespace std; const int N = 30, M = 100010; struct edge {int u, v;} e [M]; int vis [N], in [N], out [N], par [N], m, OK; int Find (int x) {int r = x, tmp; while (par [r]> = 0) r = par [r]; while (x! = R) {tmp = par [x]; par [x] = r; x = tmp;} return r;} void Union (int u, int v) {int ru = Find (u), rv = Find (v), tmp = par [ru] + par [rv]; if (par [ru] <par [rv]) par [rv] = ru, par [ru] = tmp; else par [ru] = rv, par [rv] = tmp;} void connect () {memset (par, -1, sizeof (par); // initialize and query the set for (int I = 0; I <m; ++ I) {int u = e [I]. u, v = e [I]. v; if (Find (u )! = Find (v) Union (u, v) ;}for (int I = 0; I <26; ++ I) for (int j = 0; j <26; ++ j) if (vis [I] & vis [j] & Find (I )! = Find (j) OK = 0;} int main () {char s [1005]; int u, v, cas; scanf ("% d", & cas ); while (cas --) {for (int I = 0; I <26; ++ I) vis [I] = in [I] = out [I] = 0; scanf ("% d", & m); for (int I = 0; I <m; ++ I) {scanf ("% s", s ); u = s [0]-'A', v = s [strlen (s)-1]-'A'; vis [u] = vis [v] = 1; e [I]. u = u, e [I]. v = v; ++ in [u], ++ out [v];} int id = 0, od = 0; // I [d] number of points with a record entry degree greater than 1 o [d] small 1 OK = 1; for (int I = 0; I <26; ++ I) {if (! Vis [I]) continue; int k = in [I]-out [I]; if (k <-1 | k> 1) {OK = 0; break ;} if (k = 1) + + id; if (k =-1) + + od;} if (id> 1 | od> 1 | id-od) OK = 0; connect (); if (OK) printf ("Ordering is possible. \ n "); else printf (" The door cannot be opened. \ n ") ;}return 0 ;}
Description:
Some secrets contain an interesting word fan. Archaeologists can open the door only by unlocking the word fans. Since there is no other way to open the door, it is important to be confused. Each door has many disks. There is a word on each disk. these disks must be rearranged so that the first denominator of each word is the same as the last letter of the previous word. For example, the word "acm" can be followed by the word "motorola. Your task is to write a program, read a group of words, and then determine whether it can be reorganized to make the first letter of each word the same as the last letter after the previous single word, in order to open the door.
Input description:
The input file contains T test data. The first line of the input file is T, followed by T test data. The first line of each test data is an integer N, indicating the number of words (1 ≤ N ≤ 100000); next there are N rows, each row is a word; each word must have at least two or at most 1000 lower-case letters. that is, only the letters 'a' ~ may appear in the word '~ 'Z'; a word may appear multiple times in the same test data.
Output description:
Output "Ordering is possible." to meet The requirements, otherwise output "The door cannot be opened .".
Sample Input
32acmibm3acmmalformmouse2okok
Sample Output
The door cannot be opened.Ordering is possible.The door cannot be opened.