我们需要在两个部分上构造一个每个都有N个顶点的二分图,并且边的总数等于M.
给定四个整数N,M,X,Y,我们需要构造一些满足该性质的二分图。如果没有任何这样的图表,那么也告诉他们。
示例: 如果N = 2,则M = 3,X = 1且Y = 2 那么二分图中的3个边将是:(1,1),(2,2)和(1,2)
如果N = 2,M = 3,X = 1且Y = 1则不存在二分图。
如果
,如何解决这个问题1 ≤ N ≤ 100
1 ≤ X ≤ Y ≤ N
0 ≤ M ≤ N * N
原始问题link
答案 0 :(得分:1)
显然,变量需要满足:
X * N <= M <= Y * N
否则,将无法解决。
找到边缘可以在波浪中完成。首先将第一组中的每个节点i
连接到第二组中的相应节点i
。在下一个wave中,将i
与(i + 1) mod N
联系起来。然后i
与(i + 2) mod N
一样。这将使每个顶点中的每个顶点的度数增加一个。只要构造了M
边,就停止。这也可能发生在浪潮中。
答案 1 :(得分:0)
ACM ICPC 2016年印度初步问题。
比赛现已结束。我无法提交答案(即将在结束前10秒提交代码并且我的互联网停止工作)。
在问题的OP版本中, d
相当于X
。
D
相当于Y
。
t
是测试用例的数量。
我根据链接中的原始问题制作了代码。
逻辑类似于
Nico Schertler是一个。我的复杂性会更多一些,因为我没有在第i+x
次迭代中将i
节点连接到x
,而是使用了一个集合来查找未连接的第一个元素。范围[1..N]
并连接它们。
这是我的代码:
#include <bits/stdc++.h>
using namespace std;
int main() {
int t, n, m, d, D;
cin >> t;
while(t--) {
cin >> n >> m >> d >> D;
if(n*D < m || n*d > m)
printf("-1\n");
else {
vector <set <int> > v(n);
int edges = 0, count = 0;
while(count != d) {
for(int i = 0; i < n; i++) {
for(int j = 0; j < n; j++) {
if(v[i].find(j) == v[i].end()) {
v[i].insert(j);
++edges;
break;
}
if(edges == m)
break;
}
if(edges == m)
break;
}
++count;
}
while(edges < m) {
for(int i = 0; i < n; i++) {
if(v[i].size() == D)
continue;
for(int j = 0; j < n; j++) {
if(v[i].find(j) == v[i].end()) {
v[i].insert(j);
++edges;
break;
}
if(edges == m)
break;
}
if(edges == m)
break;
}
}
for(int i = 0; i < n; i++) {
set <int>::iterator it = v[i].begin();
for(; it != v[i].end(); ++it) {
printf("%d %d\n", i+1, (*it)+1);
}
}
}
}
return 0;
}
我不知道这段代码是否正确。