WuliWuliiii
凤兮凤兮归故乡 遨游四海求其凰

题目链接

  有N个字符串,现在要求我们输出1~N个字符串的首尾相接串,并且字典序最小。

  所以,首先对N个字符串sort一下,然后再是进行处理,我们可以用一个栈来维护答案,然后为了避免访问重复的字符串,所以,每个点用一个队列去进行维护,然后用过之后就弹出,复杂度为O(N)。其余的,就是欧拉通路的基本操作了。

#include <iostream>
#include <cstdio>
#include <cmath>
#include <string>
#include <cstring>
#include <algorithm>
#include <limits>
#include <vector>
#include <stack>
#include <queue>
#include <set>
#include <map>
#include <bitset>
#define lowbit(x) ( x&(-x) )
#define pi 3.141592653589793
#define e 2.718281828459045
#define INF 0x3f3f3f3f
#define HalF (l + r)>>1
#define lsn rt<<1
#define rsn rt<<1|1
#define Lson lsn, l, mid
#define Rson rsn, mid+1, r
#define QL Lson, ql, qr
#define QR Rson, ql, qr
#define myself rt, l, r
#define pii pair<int, int>
#define MP(a, b) make_pair(a, b)
using namespace std;
typedef unsigned long long ull;
typedef unsigned int uit;
typedef long long ll;
const int maxN = 30;
int N, in_du[maxN], out_du[maxN], root[maxN];
int fid(int x) { return x == root[x] ? x : root[x] = fid(root[x]); }
bool vis[maxN];
struct Eddge
{
    int u, to, id;
    Eddge(int a=0, int b=0, int c=0):u(a), to(b), id(c) {}
} edge[1005];
queue<Eddge> to[maxN];
void addEddge(int u, int v, int w)
{
    edge[w] = Eddge(u, v, w);
    to[u].push(Eddge(u, v, w));
    out_du[u] ++; in_du[v] ++;
}
stack<int> st;
void dfs(int u)
{
    while(!to[u].empty())
    {
        int v = to[u].front().to, id = to[u].front().id; to[u].pop();
        dfs(v);
        st.push(id);
    }
}
string s[1005];
int main()
{
    int T; scanf("%d", &T);
    while(T --)
    {
        scanf("%d", &N);
        memset(vis, false, sizeof(vis));
        for(int i = 1; i <= 26; i ++) while(!to[i].empty()) to[i].pop();
        for(int i = 1; i <= 26; i ++) root[i] = i;
        for(int i = 1; i <= 26; i ++) in_du[i] = out_du[i] = 0;
        for(int i = 1; i <= N; i ++) cin >> s[i];
        sort(s + 1, s + N + 1);
        int beg = 1;
        for(int i = 1, len, u, v, fu, fv; i <= N; i ++)
        {
            len = (int)s[i].size();
            u = s[i][0] - 'a' + 1;
            if(i == 1) beg = u;
            v = s[i][len - 1] - 'a' + 1;
            vis[u] = vis[v] = true;
            addEddge(u, v, i);
            fu = fid(u); fv = fid(v);
            if(fu ^ fv) { root[fu] = fv; }
        }
        int sum = 0; bool ok = true;
        for(int i = 1; i <= 26; i ++) if(vis[i] && fid(i) == i) sum ++;
        if(sum > 1) ok = false;
        sum = 0;
        int sta = 0, end = 0;
        for(int i = 1; ok && i <= 26; i ++) if(vis[i])
        {
            if(abs(in_du[i] - out_du[i]) == 1)
            {
                sum ++;
                if(in_du[i] > out_du[i]) end ++;
                else sta ++;
            }
            else if(abs(in_du[i] - out_du[i]) > 1) ok = false;
        }
        if(sum > 2) ok = false;
        if(ok && (sum == 0 || (sum == 2 && sta == 1 && end == 1)))
        {
            while(!st.empty()) st.pop();
            if(!sum)
            {
                dfs(beg);
            }
            else
            {
                for(int i = 1; i <= N; i ++) if(out_du[edge[i].u] > in_du[edge[i].u])
                {
                    beg = edge[i].u;
                    break;
                }
                dfs(beg);
            }
            while(!st.empty())
            {
                cout << s[st.top()]; st.pop();
                printf(st.empty() ? "\n" : ".");
            }
        }
        else printf("***\n");
    }
    return 0;
}
/*
1
5
aa
ab
aba
ba
bb
*/

 

posted on 2020-12-01 16:02  唔哩Wulili  阅读(108)  评论(0编辑  收藏  举报