今晚也照常打了比赛,上午看有人发消息说A题特别难,所以我打比赛的时候就一直都没看A题。开始先看了D题,觉得不是特别难,看了一下榜,发现B题大家都过了,就先去做了B,B也是个水题就比较容易的过了。然后我又去做D题,代码写出来之后提交WA了,一看代码,多判断了一种情况,然后我又把这种情况删了又叫了一发,还是WA,改了两遍都不对,后来才知道少加了一个判断条件,真的是太粗心了,明明都不应该错。
C题和E题都是广搜题,由于我对搜索这一块不是很熟,不会代码实现,就想着做做练练,我看了一下题意,感觉C题相比较E更简单,就开始做C。做C的时候参考了题解,因为我一直做不对,就看了别人的题解,看别人是怎么实现的,发现人家的代码真的是即常规又巧妙,自己的水平还是太低。对于掌握搜索的最好方法可能就是熟能生巧吧,只理解理论知识是远远不够的,题该刷了还是要刷的,从简单一直加大难度,在做题的过程中我们才能自己总结出规律,这样以后遇到DFS或者BFS问题才不会觉得无处下手。我的水平还是太低,好多人都会写的题我就没有做出来,还是要更加倍努力。
今天白天我看的正好也是搜索。
树和图的遍历
深度优先遍历模板:
void dfs(int x)
{
v[x]=1;///记录点x被访问过
for(int i=head[x];i;i=next1[i])
{
int y=ver[i];
if(v[y])
continue;
dfs(y);
}
}
广度优先遍历模板:
void bfs()
{
memset(d,0,sizeof(d));
queue<int>q;
q.push(1);
d[1]=1;
while(q.size()>0)
{
int x=q.front();
q.pop();
for(int i=head[x];i;i=next1[i])
{
int y=ver[i];
if(d[y])
continue;
d[y]=d[x]+1;
q.push(y);
}
}
}
拓扑排序
是给有向无环图排序,入度小于等于1 的点可以入队,父亲节点在字节点前,按层排序。
void add(int x,int y)///在邻接表中添加一条有向边
{
ver[++tot]=y,next1[tot]=head[x],head[x]=tot;
deg[y]++;
}
void topsort()
{
queue<int>q;
for(int i=1;i<=n;i++)
if(deg[i]==0)
q.push(i);
while(q.size())
{
int x=q.front();
q.pop();
a[++cnt]=x;
for(int i=head[x];i;i=next[i])
{
int y=ver[i];
if(--deg[y]==0)
q.push(y);
}
}
}
int main()
{
cin>>n>>m;///点数和边数
for(int i=1;i<=m;i++)
{
int x,y;
cin>>x>>y;
add(x,y);
}
topsort();
for(int i=1;i<=cnt;i++)
cout<<a[i]<<endl;
cout<<endl;
}