第十一周总结

先来说一下,对这个课的感受,学习到了什么:在大学里一直是一个比较自律的人,即使在学习能力相对较弱的情况下,还是义无反顾的选择了这门课,上大学以前谁能想到我曾经是一个对游戏极度痴狂的人,上大学以后顿悟了,从那一刻开始到现在我一直在建立一个基础薄弱的新的体系,一个能让我看到光明的新体系,用于摆脱过去的旧模式(每天只想着游戏),建立一个与过去完全不同的体系,可想而知这个过程必定是艰难的,首先就表现在对知识开始学习的困难,慢,效率极低,入门难于其他人,就上学期的程序设计而言,我用来写代码的时间特别多,但这仅仅是刚达到其他同学用较短时间完成的任务量,也没能达到老师的要求,我知道这是我当下能力的表现,但我始终坚信积累多了会变得和以前不一样、一切会好起来,在寒假的时候,我也在一点点的改变自己,把洛谷上的题接着往下做,我只能通过这种方式来进行学习,如果不通过这个方式,对那个时候极不稳定的体系就会崩塌,收益降低,所以我只能一点点的建立、一点点的改变,大一下学期开学后,再回看大一上学期切实的感受到了自己真的不一样了,选择这门课后,我其实就知道以我当下之能力,我根本无法很好的结束课程的学习和得不到一个好的睡眠,但就是想试一试,就是试一试,课开始后我也切实的感悟到费老师的觉悟之高,也深深感染了我,现在也建立起一个了解别人的思路(看资料和看题解)-写博客督促自己-自己做题,这种方式进行学习。要问我学到了什么,除了知识以外,也说不清自己哪里改变(我认为短期是难以改变我自己的,但学了改变的方法以后,虽对当下影响微乎其微,但我相信在日后定会迸发新的生机),感觉一切都往好的方向发展,也促进了我新体系的建立,为以后的学习积攒了力量。学这门课对我来说,虽降低学分绩点,但提高了人生高度。

总结:这一个星期我把上个星期看的几道题全做完了,另外又多做了一些没看的题,涉及的题没有拓扑排序的,全做了一些并查集的简单题,算是吧。

做的题虽简单但是我还是想分享几道题:

1、P2814 家谱 - 洛谷 | 计算机科学教育新生态 (luogu.com.cn)

题意:输入多行字符串,一系列有关父子关系的描述,#name为父亲,下面带着若干字符串+name为儿子,再接下来?name代表求该人最早的祖先,如果遇到$代表结束。

思路:存储数据是关键,用map存储即可,处理好数据后,初始化,将父亲与孩子相连,然后查找给定人的祖先。

以下是我写的代码,可以说map真的是好用。

#include<bits/stdc++.h>
using namespace std;
string a,b;
map<string,string> c;
map<int,string> d;
map<int,char> e;
char f;
int g,h;
map<int,string> m;
string find(string s){
      return c[s]==s?s:c[s]=find(c[s]);
}
int main(){
    while(1){
        cin>>f;
        if(f=='$') break;
        cin>>a;
        if(f=='#'||f=='+'){
        e[++g]=f;
        d[g]=a;
        }
        else
            m[++h]=a;
    }
    for(int i=1;i<=g;i++)
        c[d[i]]=d[i];
    for(int i=1;i<=g;i++){
        if(e[i]=='#')
            b=d[i];
        else
            c[d[i]]=b;
    }
    for(int i=1;i<=h;i++){
        cout<<m[i]<<" "<<find(m[i])<<endl;
    }
    return 0;
}

2、P2256 一中校运会之百米跑 - 洛谷 | 计算机科学教育新生态 (luogu.com.cn)

题意:共有N个参赛选手,给你选手的名字,m句话告诉你那俩同学一组,老师问你k句话,问你俩人是否一组,如果一组输出Yes.,否则输出No.。

思路:使用map对并查集根节点进行初始化,把给的每两个结点并起来,再进行寻找给予两个人的根节点是否相同,如果相同输出Yes.,否则输出No.。

这道题存数据也是关键。

#include<bits/stdc++.h>
using namespace std;
int n,m,k;
map<string,string> ma;
string x,y;
string find(string s){
     return ma[s]==s?s:ma[s]=find(ma[s]);
}
int main(){
    cin>>n>>m;
    for(int i=1;i<=n;i++){
        cin>>x;
        ma[x]=x;
    }
    for(int i=1;i<=m;i++){
        cin>>x>>y;
        string fx=find(x),fy=find(y);
        if(fx!=fy) ma[fx]=fy;
    }
     cin>>k;
     for(int i=1;i<=k;i++){
        cin>>x>>y;
        string fx=find(x),fy=find(y);
        if(fx==fy) cout<<"Yes."<<endl;
        else
            cout<<"No."<<endl;
     }
}

3、​​​​​​P2661 [NOIP2015 提高组] 信息传递 - 洛谷 | 计算机科学教育新生态 (luogu.com.cn)

题意:有n个同学正在玩信息传递游戏,每个人有一个固定的信息传递对象,编号为i的同学的信息传递对象是编号为Ti的同学,游戏开始每个人都只知道自己的生日,之后每一轮,所有人会同时将自己当前所知的信息告诉各自的信息传递对象,当有人从别人口中得知自己的生日时游戏结束,问该游戏可以进行几轮。

思路:

先用并查集判断是否构成一个环,如果是的话,我们就可以记录下这个答案,然后是最小的答案。那么,如果构成一个环的话,怎么记录它的长度呢?我们可以先定义一个临时变量sum,在并查集找祖先的函数中使cnt的值加1,最后函数结束时就能得到这个环的长度了,同时,如果构成了一个环,就不需要把这个环的结尾接上,否则会陷入死循环!

#include <bits/stdc++.h>
using namespace std;
const int N = 200010;
int n, fa[N], sum= 0x3f3f3f3f;
int find(int x, int &cnt) {
    sum ++;
    if (fa[x] == x) return x;
    else return find(fa[x], cnt);
}
int main () {
    scanf("%d", &n);
    for (int i = 1; i <= n; i ++)
        fa[i] = i;
    for (int i = 1; i <= n; i ++) {
        int sum= 0, f;
        scanf("%d", &f);
        if (find(f, cnt) == i) {
            sum= min(ans, sum);
        }else
        	fa[i] = f;
    }
    printf("%d", sum);
    return 0;
}

现在我所涉及到的并查集,就是单纯的合并,寻找祖先结点,如何更好存数据、生成最小树等问题,现在慢慢提高,在接下来的几周希望可以学到更多东西。

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值