今天记单词记了一个小时。(1h)
发现自己对“树”的理解还不够清晰、深刻,又花了两个小时左右看了看b站上的视频以及阅读了一些博客来加深自己的理解。(2h)
做了两道洛谷上的《并查集与树》的题组中的两道题,分别是:新二叉树 - 洛谷,【模板】并查集 - 洛谷
题目:
新二叉树 - 洛谷 ( 2h )
这道题就是一道很基础的二叉树的题,刚好可以让我加深一下对“树”的理解。
题目会输入n组数据,每组数据都有三个字符,依次表示当前节点(父节点)、当前节点的左子节点以及右子节点。
因此,我设立了一个结构体数组,包含两个结构体指针变量以及一个char型成员变量。随后就要对有效区间内的结构体数组元素进行初始化。
然后就是常规的输入输出操作了,这里,为了方便,我设了一个传递指针参数的输出函数。
#include<stdio.h>
#include<stdlib.h>
#include<string.h>
#define f (sizeof(struct abc))
int n;
struct abc
{
char data;
struct abc * left;
struct abc * right;
}tree[10000];
struct abc * head;
void printf_tree(struct abc * k)
{
printf("%c",k->data);
if(k->left != NULL)//判断是否有左节点
printf_tree(k->left);
if(k->right != NULL)//判断是否有右节点
printf_tree(k->right);
}
int main()
{
scanf("%d",&n);
getchar();
int i,j,k1;
for(i=0;i<=n;i++)
{
tree[i].left=NULL;
tree[i].right=NULL;
tree[i].data=i;
}
for(i=1;i<=n;i++)
{
char s[4];
scanf("%s",s);//s[0]为父节点,s[1],s[2]分别为其左右子节点,s[3]用来吃掉多余的'\n'缓冲字符
if(i == 1)
head=&tree[s[0]];
tree[s[0]].data=s[0];
tree[s[1]].data=s[1];
tree[s[2]].data=s[2];
if(s[1] != '*')
tree[s[0]].left=&tree[s[1]];
if(s[2] != '*')
tree[s[0]].right=&tree[s[2]];
}
printf_tree(head);
return 0;
}
题目:
【模板】并查集 - 洛谷( 1.5h )
这道题可以说是学习“并查集”的一道很好的入门题。利用循环遍历将所有存在联系的节点的根节点统一为同一个节点,不同的根节点就表示不同的集合,这样就完成了“合并”的任务,输出时判断需询问的两个数值的节点的根节点是否相同就好了。
#include<stdio.h>
#include<stdlib.h>
#include<string.h>
int parent[1000010];
int n,m,z;
int find(int x)//找到根节点
{
if(parent[x] != x)
parent[x]=find(parent[x]);
return parent[x];
}
void union_parent(int x,int y)//统一父节点,即合并集合
{
parent[(find(x))]=find(y);
}
int main()
{
int i,j;
scanf("%d %d",&n,&m);
for(i=0;i<=n;i++)
parent[i]=i;
for(i=1;i<=m;i++)
{
int a,b;
scanf("%d %d %d",&z,&a,&b);
if(z == 1)
{
union_parent(a,b);
}
if(z == 2)
{
if(find(a) == find(b))
printf("Y\n");
else
printf("N\n");
}
}
return 0;
}
然后花了些时间做“搭配购买 - 洛谷”这一题,但是没过,只过了个样例,明天还需要继续修改
( >2h )