首页 > ACM题库 > HDU-杭电 > hdu 2144 Evolution-并查集-[解题报告]C++
2013
12-29

hdu 2144 Evolution-并查集-[解题报告]C++

Evolution

问题描述 :

  Every kind of living creatures has a kind of DNA. The nucleotide bases from which DNA is built are A (adenine), C (cytosine), G (guanine), and T (thymine). Sometimes if two DNA of two living creatures have the same substring, and the length is beyond a certain percentage of the whole length, we many consider whether the two living creatures have the same ancestor. And we can separate them into a certain species temporarily for our research, and we say the two living creatures are similar Make sure if A is similar with B, and B is similar with C, but C is not similar with A, we also separate A, B and C into a kind, for during the evolution, there happens aberrance.
Now we have some kinds of living creatures and their DNA, just tell us how many kinds of living creatures we can separate.

输入:

  There are a lot of cases. In each case, in the first line there are two numbers N and P. N means the number of kinds of living creatures. If two DNA are similar, there exist a substring, and its length is beyond the percentage of any DNA of the two, and P is just the percentage. And 1<=N<=100, and 1<=P<100 (P is 100, which means two DNA are similar if and only if they are the same, so we make sure P is smaller than 100). The length of each DNA won’t exceed 100.

输出:

  There are a lot of cases. In each case, in the first line there are two numbers N and P. N means the number of kinds of living creatures. If two DNA are similar, there exist a substring, and its length is beyond the percentage of any DNA of the two, and P is just the percentage. And 1<=N<=100, and 1<=P<100 (P is 100, which means two DNA are similar if and only if they are the same, so we make sure P is smaller than 100). The length of each DNA won’t exceed 100.

样例输入:

3 10.0
AAA
AA
CCC

样例输出:

Case 1:
2

点击打开链接

/*

参考大神Ice_Crazy:点击打开链接
有点坑,代码敲了5遍,没有debug出来。。
第五遍果断AC了!!!!
用并查集判断。
如果满足加入标记。。。


2013/04/22-10:31
*/

#include"stdio.h"
#include"string.h"
const int N=120;
int dp[N][N];
char str[N][N];
int len[N],set[N];
int find(int x)
{
	if(x==set[x])return x;
	set[x]=find(set[x]);
	return set[x];
}
int fun(int x,int y)
{
	int i,j;
	int max;
	memset(dp,0,sizeof(dp));
	max=0;
	for(i=1;i<=len[x];i++)
	{
		dp[i][0]=0;
		for(j=1;j<=len[y];j++)
		{
			if(str[x][i]==str[y][j])dp[i][j]=dp[i-1][j-1]+1;
			else dp[i][j]=0;
			if(dp[i][j]>max)max=dp[i][j];
		}
	}
	return max;
}
int main()
{
	int T;
	int a,b;
	int i,j;
	int n,t;
	double p;
	T=1;
	while(scanf("%d%lf",&n,&p)!=-1)
	{
		for(i=0;i<n;i++)
			set[i]=i;
		for(i=0;i<n;i++)
		{
			scanf("%s",str[i]+1);
			str[i][0]=' ';
			len[i]=strlen(str[i])-1;
			for(j=0;j<i;j++)
			{
				a=find(i);
				b=find(j);
				if(a==b)continue;
				t=fun(i,j);
				if(t*100.0/len[i]>p&&t*100.0/len[j]>p)
					set[a]=b;
			}
		}
		int ans;
		ans=0;
		for(i=0;i<n;i++)
			if(set[i]==i)ans++;
		printf("Case %d:\n",T++);
		printf("%d\n",ans);
	}
	return 0;
}

解题转自:http://blog.csdn.net/yangyafeiac/article/details/8834054


  1. 嗯 分析得很到位,确实用模板编程能让面试官对你的印象更好。在设置辅助栈的时候可以这样:push时,比较要push的elem和辅助栈的栈顶,elem<=min.top(),则min.push(elem).否则只要push(elem)就好。在pop的时候,比较stack.top()与min.top(),if(stack.top()<=min.top()),则{stack.pop();min.pop();},否则{stack.pop();}.

  2. 第二个方法挺不错。NewHead代表新的头节点,通过递归找到最后一个节点之后,就把这个节点赋给NewHead,然后一直返回返回,中途这个值是没有变化的,一边返回一边把相应的指针方向颠倒,最后结束时返回新的头节点到主函数。