• hdu2328 后缀树


    #include <cstdio>
    #include <cstdlib>
    #include <cstring>
    #include <cmath>
    #include <algorithm>
    #include <queue>
    #include <stack>
    #include <deque>
    #include <iostream>
    using namespace std;
    typedef long long LL;
    const int MOD = 1000000007;
    const int maxn = 40009 + 5;
    
    int tree[maxn][30];
    int sum[maxn];
    int tot;
    char ss[maxn], mid[maxn], ans[maxn];
    
    void insert(char *str)
    {
    	int len = strlen(str);
    	int root = 0;
    	for (int i = 0; i < len; i++)
    	{
    		int id = str[i] - 'a';
    		if (!tree[root][id])
    			tree[root][id] = ++tot;
    
    		if (sum[tree[root][id]] + 1 >= 1)
    		{
    			sum[tree[root][id]] = 1;
    		}
    		else
    		{
    			break;
    		}
    	
    		root = tree[root][id];
    	
    	}
    }
    
    int find(char *str, int x)
    {
    	int len = strlen(str);
    	int root = 0, deep = 0;
    	for (int i = 0; i < len; i++)
    	{
    		int id = str[i] - 'a';
    		if (tree[root][id])
    		{
    			if (sum[tree[root][id]] + 1 >= x)
    			{
    				sum[tree[root][id]] = x;
    				deep++;
    			}
    			else
    			{
    				break;
    			}
    			root = tree[root][id];
    		}
    		else
    		{
    			break;
    		}
    	}
    
    	return deep;
    }
    
    int main()
    {
    
    	int n, i, j, k, head;
    
    	while (scanf("%d", &n) != EOF)
    	{
    		if(n == 0)
    			break;
    
    		memset(tree, 0, sizeof(tree));
    		memset(sum, 0, sizeof(sum));
    		memset(ans, 0, sizeof(ans));
    		tot = 1;
    
    		for (i = 1; i < n; i++)
    		{
    			scanf(" %s", ss);
    			k = strlen(ss);
    			//cout << "input: " << ss << endl;
    			if (i == 1)
    			{
    				for (j = 0; j < k; j++)
    				{
    					//	printf("%s
    ", &ss[j]);
    					insert(&ss[j]);
    				}
    			}
    			else
    			{
    				for (j = 0; j < k; j++)
    				{
    					find(&ss[j], i);
    				}
    			}
    		}
    
    		head = 0;
    		scanf(" %s", ss);
    		//cout << "Nth: " << ss << endl;
    		k = strlen(ss);
    		//		cout << "follows " << endl;
    		for (j = 0; j < k; j++)
    		{
    			//	cout << &ss[j] << endl;
    			int len = find(&ss[j], n);
    			
    			mid[0] = 0;
    			strncpy(mid, ss + j, len);
    mid[len] = 0;
    			//	printf("mid:  %s
    ", mid);
    
    			if (len > head || (len == head && strcmp(mid, ans) < 0))
    			{
    				head = len;
    				ans[0] = 0;
    				strcpy(ans, mid);
    				//	printf("ans:  %s
    ", ans);
    			}
    		}
    
    		if (head == 0)
    		{
    			printf("IDENTITY LOST
    ");
    		}
    		else
    		{
    			printf("%s
    ", ans);
    		}
    		//	cout << " n:  " << n << endl;
    	}
    
    	return 0;
    }
    

    后缀树的思想和字典树一样,不过是依次把字符串的所有后缀加入到树中。

    需要整理的知识:后缀树的O(n)优化、后缀自动机、后缀数组

  • 相关阅读:
    汉语-词语-平目:百科
    汉语-词语-平昔:百科
    汉语-词语-平一:百科
    汉语-词语-平居:百科
    汉语-词语-平展:百科
    汉语-词语-平静:百科
    汉语-词语-平心:百科
    汉语-词语-平庸:百科
    汉语-词语-平常:百科
    1231 最优布线问题
  • 原文地址:https://www.cnblogs.com/daybreaking/p/11707929.html
Copyright © 2020-2023  润新知