Repository

Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/65536 K (Java/Others)
Total Submission(s): 6444    Accepted Submission(s):
2096

Problem Description
When you go shopping, you can search in repository for
avalible merchandises by the computers and internet. First you give the search
system a name about something, then the system responds with the results. Now
you are given a lot merchandise names in repository and some queries, and
required to simulate the process.
 
Input
There is only one case. First there is an integer P
(1<=P<=10000)representing the number of the merchanidse names in the
repository. The next P lines each contain a string (it's length isn't beyond
20,and all the letters are lowercase).Then there is an integer
Q(1<=Q<=100000) representing the number of the queries. The next Q lines
each contains a string(the same limitation as foregoing descriptions) as the
searching condition.
 
Output
For each query, you just output the number of the
merchandises, whose names contain the search string as their substrings.
 
Sample Input
20
ad
ae
af
ag
ah
ai
aj
ak
al
ads
add
ade
adf
adg
adh
adi
adj
adk
adl
aes
5
b
a
d
ad
s
 
Sample Output
0
20
11
11
2
 
Source
 
Recommend
gaojie   |   We have carefully selected several similar
problems for you:  2852 2847 2845 2850 2851 
 
根据题意可知:题目属于判断字符串中是否包含子串的问题,对于一般的字典树,用来判断前缀,而这里不能直接这么去建树。在建树的时候将字符串X=X1X2....Xn的分别以X1,X2....Xn开头的后缀子串插入到Trie树中,如此一来就可以判断某个字符串是否被包含在另一个字符串当中。但是这就有一个问题,比如插入了字符串abab,那么当查找字符串ab时就会重复计数,因此需要多设计一个标识以表示在插入"abab"和"ab"时时同一个字符串即可(是同一个字符串就不需要使计数器加1),因此在Trie树结点中多设计一个商品id来标记。id用来记录最后一个经过此路径上的商品编号,如果要插入的字符串编号同当前节点的编号不同,则计数器加1,并且将当前结点的编号置为要插入的字符串的编号。
 
 
经验:对字符串的处理还可以这样insert(root, s + j, i);,void insert(trie*root, char *s, int id),*s就是某个s[i],s++就相当于i++
 #include <iostream>
#include<cstring>
#include <cstdio>
#include<string>
#include <algorithm>
using namespace std; typedef struct nn
{
int count;
int id;
nn* nxt[];
}trie; void insert(trie*root, char *s, int id)
{
trie*p = root;
while (*s != '\0')//对字符串的处理还可以这样
{
if (p->nxt[*s - 'a'] == NULL)
{
trie *temp = (trie *)malloc(sizeof(trie));
for (int i = ; i<; i++)
{
temp->nxt[i] = NULL;
}
temp->count = ;
temp->id = -; //-1表示没有商品
p->nxt[*s - 'a'] = temp;
}
p = p->nxt[*s - 'a'];
if (p->id != id)
{//如果当前结点的ID不等于要插入的ID,则计数器count++,并且重新置ID的值
p->id = id;
p->count++;
}
s++;//每一个子串,不如asda里的sd
}
} int search(trie*root, char *s)
{
trie *p = root;
int i;
for (i = ; s[i] != '\0'; i++)
{
if (p->nxt[s[i] - 'a'] == NULL)
return ;
p = p->nxt[s[i] - 'a'];
}
return p->count;
} int main()
{
int i, j;
int n, m;
char s[];
trie *root = (trie*)malloc(sizeof(trie));
for (i = ; i < ; i++)
{
root->nxt[i] = NULL;
}
root->count = ;
root->id = -;
cin >> n;
for (i = ; i <= n; i++)
{
cin >> s;
int l = strlen(s);
for (j = ; j < l; j++)
{//将字符串X=X1X2...Xn的分别以X1,X2...Xn开头的后缀字符串插入到Trie树中
insert(root, s + j, i);
}
}
cin >> m;
for (i = ; i <= m; i++)
{
cin >> s;
cout << search(root, s) << endl;
}
return ;
}

HDU 2846 Repository(字典树,每个子串建树,*s的使用)的更多相关文章

  1. HDU 2846 Repository (字典树 后缀建树)

    Repository Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/65536 K (Java/Others) Total ...

  2. HDU 2846 Repository(字典树,标记)

    题目 字典树,注意初始化的位置~!!位置放错,永远也到不了终点了org.... 我是用数组模拟的字典树,这就要注意内存开多少了,,要开的不大不小刚刚好真的不容易啊.... 我用了val来标记是否是同一 ...

  3. hdu 2846 Repository (字典树)

    RepositoryTime Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/65536 K (Java/Others)Total S ...

  4. hdu 2846(字典树)

    Repository Time Limit: 2000/1000 MS (Java/Others)    Memory Limit: 65536/65536 K (Java/Others)Total ...

  5. HDU 2846 Repository(字典树)

    字典树较为复杂的应用,我们在建立字典树的过程中需要把所有的前缀都加进去,还需要加一个id,判断它原先是属于哪个串的.有人说是AC自动机的简化,但是AC自动机我还没有做过. #include<io ...

  6. hdu 2846 Repository

    http://acm.hdu.edu.cn/showproblem.php?pid=2846 Repository Time Limit: 2000/1000 MS (Java/Others)     ...

  7. hdu2846 Repository 字典树(好题)

    把每个字符串的所有子串都加入字典树,但在加入时应该注意同一个字符串的相同子串只加一次,因此可以给字典树的每个节点做个记号flag--表示最后这个前缀是属于那个字符串,如果当前加入的串与它相同,且二者属 ...

  8. hdu 1979 DFS + 字典树剪枝

    http://acm.hdu.edu.cn/showproblem.php?pid=1979 Fill the blanks Time Limit: 3000/1000 MS (Java/Others ...

  9. HDU 1671 (字典树统计是否有前缀)

    题目链接:http://acm.hdu.edu.cn/showproblem.php?pid=1671 Problem Description Given a list of phone number ...

随机推荐

  1. Mininet实验 自定义拓扑结构

    参考:MiniNet实验2 通过Mininet学习可视化操作,可以在界面上方便的构建拓扑结构. 最新的Mininet 2.2.0内置了一个mininet可视化工具miniedit.miniedit在/ ...

  2. UVa 12169 不爽的裁判

    https://vjudge.net/problem/UVA-12169 题意: 输入T,x1,x2,x3,...,x2T-1,输出x2,x4,...,x2T. 递推公式为xi=(axi-1+b)mo ...

  3. Validate Binary Search Tree,判断是否是二叉排序树

    算法分析:两种方法,一种是中序遍历,然后得到一个序列,看序列是否是有序的.第二种,是用递归. 中序遍历: public class Solution { List<Integer> lis ...

  4. shell 判断字符串长度是否不为0

    test.sh #!/bin/bash s1="" if test $s1 ;then echo "length is not zero" else echo ...

  5. 菜单项onCreateOptionsMenu()和onOptionsItemSelected()的使用

    Java源文件 package com.example.macname.myapplication; import android.support.v7.app.AppCompatActivity; ...

  6. js 杂谈

    js解释器有自己的内存管理机制(垃圾回收:自动回收无引用指向对象) js采用一种数字类型(64位浮点数),100与1e2完全相等 条件判断是被当为假的值:false.null.undefined.‘’ ...

  7. 最小生成树prim和kruskal模板

    prim: int cost[MAX_V][MAX_V]; //cost[u][v]表示边e=(u,v)的权值(不存在的情况下设为INF) int mincost[MAX_V]; //从集合X出发的每 ...

  8. 动态创建OATipBean

    动态创建OATipBean. 动态创建的OATipBean无法直接设置提示内容,需要添加一个静态文本. 参考User Guide示例如下. If you need to create a tip pr ...

  9. Linux终端界面屏保

    Linux终端界面屏保   在很多Linux使用者的认知里,都认为终端下的Linux操作界面是没有屏保的,只有像windows那样的图形界面下才有屏保.但是其实Linux下也是有屏保的,只不过是ASC ...

  10. python学习笔记(四)---python不能输出中文问题

    只需要在所有代码的最前面加上:#coding:utf-8 即可