USACO2.3.5 Controlling Companies 控制公司(dfs)

版权声明:本文为博主原创文章,转载注明出自CSDN bestsort。 https://blog.csdn.net/bestsort/article/details/82851597

Description
有些公司是其他公司的部分拥有者,因为他们获得了其他公司发行的股票的一部分。例如,福特公司拥有马自达公司12%的股票。据说,如果至少满足了以下条件之一,公司A就可以控制公司B了: 公司A = 公司B。 公司A拥有大于50%的公司B的股票。 公司A控制K(K >= 1)个公司,记为C1, …, CK,每个公司Ci拥有xi%的公司B的股票,并且x1+ … + xK > 50%。 你将被给予一系列的三对数(i,j,p),表明公司i享有公司j的p%的股票。计算所有的数对(h,s),表明公司h控制公司s。至多有100个公司。 写一个程序读入三对数(i,j,p),i,j和p是都在范围(1…100)的正整数,并且找出所有的数对(h,s),使得公司h控制公司s。

Input
第一行: N,表明接下来三对数的数量。 第二行到第N+1行: 每行三个整数作为一个三对数(i,j,p),如上文所述。

Output
输出零个或更多个的控制其他公司的公司。每行包括两个整数表明序号为第一个整数的公司控制了序号为第二个整数的公司。将输出的每行以第一个数字升序排列(并且第二个数字也升序排列来避免并列)。请不要输出控制自己的公司。

Sample Input
3
1 2 80
2 3 80
3 1 20

Sample Output
1 2
1 3
2 3


第一次看到这个题以为是并查集…然后发现好像可以暴力!?,结果在交了N发Wrong AnswerTLE后(我可还专门用了vector来优化遍历的次数了啊啊啊!!!),想了想,还是用dfs做好了,每次对一个点遍历,找出它所有的子公司,然后输出.想了想时间复杂度 O ( N 3 ) O(N^3) ( N N 为结点数),这题最多也就才 1 e 6 1e6 的运算量,但是写出来的时候还是感觉会T(不然我前面怎么T的…我也很迷),结果过了…过了?!?
代码在下面


#include <map>
#include <queue>
#include <cstdlib>
#include <cmath>
#include <cstdio>
#include <string>
#include <cstring>
#include <fstream>
#include <iostream>
#include <sstream>
#include <algorithm>
#define lowbit(a) (a&(-a))
#define _mid(a,b) ((a+b)/2)
#define _mem(a,b) memset(a,0,(b+3)<<2)
#define fori(a) for(int i=0;i<a;i++)
#define forj(a) for(int j=0;j<a;j++)
#define ifor(a) for(int i=1;i<=a;i++)
#define jfor(a) for(int j=1;j<=a;j++)
#define mem(a,b) memset(a,b,sizeof(a))
#define IN freopen("in.txt","r",stdin)
#define OUT freopen("out.txt","w",stdout)
#define IO do{\
    ios::sync_with_stdio(false);\
    cin.tie(0);\
    cout.tie(0);}while(0)
#define mp(a,b) make_pair(a,b)
using namespace std;
typedef long long ll;
const int maxn =  1e2+10;
const int INF = 0x3f3f3f3f;
const int inf = 0x3f;
const double EPS = 1e-7;
const double Pi = acos(-1);
const int MOD = 1e9+7;
struct node {
    int y,w;
    node() {};
    node(int _y,int _w) {
        y=_y,w=_w;
    }
};
vector <int>a[maxn];
vector <node> g[maxn];//想的是用vector存图,这样遍历的时候对于边数较小的数据会节省很多时间
bool v[maxn];
int dis[maxn];
void dfs(int x){
    v[x] = true;
    for(int i=0;i<g[x].size();i++){			//g[x][i].y表示从x点->y点
        dis[g[x][i].y] += g[x][i].w;		//g[x][i].w表示从x点->y点的权值
        if(dis[g[x][i].y]>50 && !v[g[x][i].y])
            dfs(g[x][i].y);
    }
}
int main() {
    //IN;
    int n;
    cin >>n;
    int x,y,z;
    fori(n) {
        cin >> x >> y >> z;
        g[x].push_back(node(y,z));		//存图咯
        if(z>50)
            a[x].push_back(y);	//x公司控股y公司
    }
    for(int i=1; i<=100; i++)
        if(a[i].size()!=0){	
            mem(v,0);
            mem(dis,0);
            dfs(i);
            jfor(100)
                if(dis[j]>50 && j!=i)
                    cout <<i <<" " <<j<<endl;
        }
    return 0;
}

猜你喜欢

转载自blog.csdn.net/bestsort/article/details/82851597