bzoj11741174: [Balkan2007]Toponyms 字典树

貌似是裸的。。。。。。上vfk大神的码。
#include <iostream>
#include <cstdio>
using namespace std;

inline int getint(char *p)
{
	while ('0' > *p || *p > '9')
		p++;
	
	int res = *p++ - '0';
	while ('0' <= *p && *p <= '9')
		res = res * 10 + *p++ - '0';
	return res;
}

template <class T>
inline void relax(T &a, const T &b)
{
	if (b > a)
		a = b;
}

const int MaxNNode = 3000000;

inline bool isLetter(char c)
{
	return ('a' <= c && c <= 'z') || ('A' <= c && c <= 'Z') || c == ' ';
}

struct node
{
	node *son, *brother;
	int size;
	char val;
	
	inline node *next(char c)
	{
		for (node *i = son; i; i = i->brother)
			if (i->val == c)
				return i;
		return NULL;
	}
};
node pool[MaxNNode];
node *tail;
node *root;

inline node *addNext(node *p, char c)
{
	node *q;
	if (tail != pool + MaxNNode)
		q = tail++;
	else
		q = new node;
	q->son = NULL, q->size = 0;
	q->val = c, q->brother = p->son, p->son = q;
	return q;
}

inline void trie_init()
{
	tail = pool;
	root = tail++;
}

inline char *trie_insert(char *s)
{
	node *p = root;
	root->size++;
	while (isLetter(*s))
	{
		node *next = p->next(*s);
		if (!next)
			next = addNext(p, *s);
		p = next;
		p->size++;
		
		s++;
	}
	return s;
}

int best = 0;
void dfs(node *p, const int &depth)
{
	relax(best, p->size * depth);
	for (node *i = p->son; i; i = i->brother)
		dfs(i, depth + 1);
}

int main()
{
	//freopen("1174.in", "r", stdin);
	//freopen("1174.out", "w", stdout);
	
	const int BufferSize = 10 * 1024 * 1024;
	static char buffer[BufferSize + 1];
	
	int bufferLen = fread(buffer, 1, BufferSize, stdin);
	buffer[bufferLen] = '\0';
	
	char *pRead = buffer;
	
	int n = getint(pRead);
	trie_init();
	for (int i = 0; i < n; i++)
	{
		while (!isLetter(*pRead))
			pRead++;
		pRead = trie_insert(pRead);
	}
	
	dfs(root, 0);
	
	cout << best << endl;
	
	return 0;
}

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值