某近似模板题1

Posted Grary

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了某近似模板题1相关的知识,希望对你有一定的参考价值。

P2097 资料分发1
题目描述

有一些电脑,一部分电脑有双向数据线连接。如果一个电脑得到数据,它可以传送到的电脑都可以得到数据。现在,你有这个数据,问你至少将其输入几台电脑,才能使所有电脑得到数据。

输入输出格式

输入格式:
第一行两个数n,m。n是点数,m是边数。

接下来m行,每行2个整数p,q表示p到q有一条双向数据线。

输出格式:
一个整数,表示至少输入的电脑数量。

输入输出样例

输入样例#1: 复制
4 5
1 2
1 3
2 3
2 1
3 4
输出样例#1: 复制
1
说明

对于30%的数据:n<=100,m<=1000

对于60%的数据:n<=2000,m<=100000

对于100%的数据:n<=100000, m<=200000

数据不保证没有重边,不保证没有自回环

用时168-92-68-56ms

看到有人用Tarjan求强联通分量做
23333
dfs,复杂度O(n)
并查集,复杂度O(input左右)
路径压缩,读入优化

#include<iostream>
#include<cstdio>
#define N 100005
using namespace std;

int a,b;
int n,m;
int fa[N];
int siz[N];

void init(){
    for(int i=1;i<=n;++i)
        fa[i]=i;
    for(int i=1;i<=n;++i)
        siz[i]=1;
}

int find(int s){
    if(fa[s]!=s)fa[s]=find(fa[s]);
    return fa[s];
}

void read(int &s){
    char ch=getchar();
    for(;!isdigit(ch);ch=getchar());
    for(s=0;isdigit(ch);s=s*10+ch-'0',ch=getchar());
}

int faa,fab;

bool un(int a,int b){
    faa=find(a);
    fab=find(b);
    if(faa>fab){
        faa^=fab;
        fab^=faa;
        faa^=fab;
    }
    if(faa!=fab)return fa[faa]=fab,siz[fab]+=siz[faa];
    return false;
}

int ans;

int main(){
    while(~scanf("%d%d",&n,&m)){
        init();ans=n; 
        for(int i=1;i<=m;++i){
            read(a),read(b);
            if(un(a,b))ans--;
        }
        printf("%d\n",ans);
    }
    return 0;
}

以上是关于某近似模板题1的主要内容,如果未能解决你的问题,请参考以下文章

VSCode自定义代码片段1——vue主模板

代码:(bfs模板)立体推箱子

2021-12-24:划分字母区间。 字符串 S 由小写字母组成。我们要把这个字符串划分为尽可能多的片段,同一字母最多出现在一个片段中。返回一个表示每个字符串片段的长度的列表。 力扣763。某大厂面试

VSCode自定义代码片段——.vue文件的模板

线段树模板1

vscode代码片段生成vue模板