幾道字典樹題目


POJ 2418 Hardwood Species

題意:給一些字符串,按照字典序輸出他們,並且輸出頻率...........


#include <iostream>
#include <algorithm>
#include <cmath>
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <string>
#include <vector>
#include <set>
#include <queue>
#include <stack>
#include <climits>//形如INT_MAX一類的
#define MAX 100005
#define INF 0x7FFFFFFF
#define REP(i,s,t) for(int i=(s);i<=(t);++i)
#define ll long long
#define mem(a,b) memset(a,b,sizeof(a))
#define mp(a,b) make_pair(a,b)
#define L(x) x<<1
#define R(x) x<<1|1
# define eps 1e-5
//#pragma comment(linker, "/STACK:36777216") ///傳說中的外掛
using namespace std;

struct Trie {
    int next[128];
    int sum;
    char s[33];
    void init() {
        memset(next,0,sizeof(next));
        sum = 0;
    }
} a[301111];
int num,cnt,root;
char str[33];

void insert(char *key) {
    int p = root;
    for(int i=0; key[i]; i++) {
        int t = int(key[i]);
        if(a[p].next[t] == 0) {
            a[p].next[t] = ++ num;
            a[num].init();
        }
        p = a[p].next[t];
    }
    a[p].sum ++;
    a[p].s[0] = '\0';
    strcpy(a[p].s,key);
}

void dfs(int p) {
    if(a[p].sum != 0) {
        printf("%s ",a[p].s);
        printf("%.4f\n",(a[p].sum * 1.0) / cnt * 100);
    }
    for(int i=0; i<128; i++) {
        if(a[p].next[i] != 0) {
            int t = a[p].next[i];
            dfs(t);
        }
    }
}

int main() {
    root = 0; num = 0; cnt = 0;
    a[root].init();
    while(gets(str)) {
        int len = strlen(str);
        if(len == 0) break;
        cnt ++;
        insert(str);
    }
    dfs(0);
    return 0;
}



HDU 2846 Repository

題意:給定一些單詞作爲字典,和一些單詞作爲詢問,對於每個詢問,求出它在所有字典單詞中作爲單詞子串出現的次數(它只能在同一單詞中以子串形式出現一次)

對於每個字典中的單詞,讓它所有後綴都在字典樹中建樹,這樣只要在字典樹中找前綴就等同於找到子串了

需要注意的是,它只能在同一單詞中以子串形式出現一次,如:str:dddddd       則ddd在str中只出現一次,所以對於同一單詞產生的後綴,需要判重......


#include <iostream>
#include <algorithm>
#include <cmath>
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <string>
#include <vector>
#include <set>
#include <queue>
#include <stack>
#include <climits>//形如INT_MAX一類的
#define MAX 100005
#define INF 0x7FFFFFFF
#define REP(i,s,t) for(int i=(s);i<=(t);++i)
#define ll long long
#define mem(a,b) memset(a,b,sizeof(a))
#define mp(a,b) make_pair(a,b)
#define L(x) x<<1
#define R(x) x<<1|1
# define eps 1e-5
//#pragma comment(linker, "/STACK:36777216") ///傳說中的外掛
using namespace std;
int n,q,root,cnt;
char str[22];
char keyword[22];

struct Trie {
    int next[26];
    int num;
    int kind;
    void init() {
        memset(next,0,sizeof(next));
        num = 0;
        kind = -1;
    }
} a[1111111];

void insert(char *key,int id,int kind) {
    int p = root;
    for(int i=id; key[i]; i++) {
        int t = key[i] - 'a';
        if(a[p].next[t] == 0) {
            a[p].next[t] = ++cnt;
            a[cnt].init();
        }
        p = a[p].next[t];
        if(a[p].kind != kind) {
            a[p].kind = kind;
            a[p].num ++;
        }
    }
}

int query(char *key) {
    int p = root;
    int sum = 0;
    for(int i=0; key[i]; i++) {
        int t = key[i] - 'a';
        if(a[p].next[t] == 0) return 0;
        p = a[p].next[t];
    }
    sum += a[p].num;
    return sum;
}

int main() {
    root = 0;
    cnt = 0;
    scanf("%d",&n);
    for(int i=0; i<n; i++) {
        scanf("%s",str);
        int len = strlen(str);
        for(int j=0; j<len; j++)
            insert(str,j,i);
    }
    scanf("%d",&q);
    for(int i=0; i<q; i++) {
        scanf("%s",keyword);
        printf("%d\n",query(keyword));
    }
    return 0;
}

POJ 1204 Word Puzzles

題意:給定了一個1000 * 1000 的由大寫字母組成的矩陣,現在給出一些單詞,要求在矩陣中找到每個單詞,記錄首字母的位置,以及它沿着什麼方向走(8個方向,米字型)


將單詞建立字典樹,然後在矩陣中枚舉每個點作爲起點,8個方向直接找就行了..........

#include <iostream>
#include <algorithm>
#include <cmath>
#include <cstdio>
#include <cstdlib>
#include <cstring>
#include <string>
#include <vector>
#include <set>
#include <queue>
#include <stack>
#include <climits>//形如INT_MAX一類的
#define MAX 100005
#define INF 0x7FFFFFFF
#define REP(i,s,t) for(int i=(s);i<=(t);++i)
#define ll long long
#define mem(a,b) memset(a,b,sizeof(a))
#define mp(a,b) make_pair(a,b)
#define L(x) x<<1
#define R(x) x<<1|1
# define eps 1e-5
//#pragma comment(linker, "/STACK:36777216") ///傳說中的外掛
using namespace std;
int n,m,w;
struct Word {
    int x,y,dir,kind;
    char word[1111];
}s[1111];

char str[1111][1111];
int dx[] = {-1,-1,0,1,1,1,0,-1};
int dy[] = {0,1,1,1,0,-1,-1,-1};
int root , cnt ;
struct Trie {
    int next[26];
    int kind;
    void init() {
        memset(next,0,sizeof(next));
        kind = -1;
    }
}a[1111111];

void insert(char *key, int kind) {
    int p = root;
    for(int i=0; key[i]; i++) {
        int t = key[i] - 'A';
        if(a[p].next[t] == 0) {
            a[p].next[t] = ++ cnt;
            a[cnt].init();
        }
        p = a[p].next[t];
    }
    a[p].kind = kind;
}
void solve() {
    for(int i=0; i<n; i++) {
        for(int j=0; j<m; j++) {
            int t = str[i][j] - 'A';
            if(a[root].next[t] == 0) continue;
            for(int k=0; k<8; k++) {
                int p = a[root].next[t];
                int x = i, y = j;
                while(x >= 0 && x < n && y >= 0 && y < m && p) {
                    if(a[p].kind != -1) {
                        s[a[p].kind].dir = k;
                        s[a[p].kind].x = i;
                        s[a[p].kind].y = j;
                    }
                    x = x + dx[k];
                    y = y + dy[k];
                    int t = str[x][y] - 'A';
                    p = a[p].next[t];
                }
            }
        }
    }
    for(int i=0; i<w; i++) {
        printf("%d %d %c\n",s[i].x,s[i].y,s[i].dir + 'A');
    }
}

int main() {
    while(scanf("%d%d%d",&n,&m,&w) != EOF) {
        root = 0; cnt = 0;
        for(int i=0; i<n; i++) scanf("%s",str[i]);
        for(int i=0; i<w; i++) {
            scanf("%s",s[i].word);
            s[i].kind = i;
            insert(s[i].word,i);
        }
        solve();
    }
    return 0;
}


待續.....


發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章