161 lines
7.3 KiB
C++
161 lines
7.3 KiB
C++
|
//
|
|||
|
// Created by 423A35C7 on 2023-12-02.
|
|||
|
//
|
|||
|
|
|||
|
#include <iostream>
|
|||
|
#include "graph.hpp"
|
|||
|
// 这次执行一轮后不一定结束了,
|
|||
|
void one_turn(ComplexGraph* graph) {
|
|||
|
for (int start = 0; start < graph->node_num; ++start) {
|
|||
|
int target;
|
|||
|
while (true) {
|
|||
|
int* target_ptr = std::min_element(graph->adjacency[start],
|
|||
|
graph->adjacency[start] + graph->node_num);
|
|||
|
// 如果最小的目标城市距离都是INT_MAX,则说明start与所有城市都已连通,则不再修建
|
|||
|
if (*target_ptr == INT_MAX) {
|
|||
|
return;
|
|||
|
}
|
|||
|
target = target_ptr - graph->adjacency[start];
|
|||
|
// 如果在同一个城市联盟内,那么把这个目标城市排除,在剩下的目标城市中继续
|
|||
|
if (graph->same_league(start, target)) {
|
|||
|
graph->adjacency[start][target] = INT_MAX;
|
|||
|
continue;
|
|||
|
}
|
|||
|
// 如果已经修建过了,则换个目标城市
|
|||
|
if (graph->incidence[start][target]) {
|
|||
|
continue;
|
|||
|
}
|
|||
|
// 不需要考虑三个或以上成环的情况
|
|||
|
break;
|
|||
|
}
|
|||
|
const int start_alpha = graph->get_alpha(start);
|
|||
|
const int target_alpha = graph->get_alpha(target);
|
|||
|
// 当城市规模系数α到达限定系数β后,我们认为该 league
|
|||
|
// 已经到达“稳定”,不再与任何其他城市修建公路。
|
|||
|
if (start_alpha >= graph->beta || target_alpha >= graph->beta) {
|
|||
|
continue;
|
|||
|
}
|
|||
|
if (start_alpha < target_alpha) {
|
|||
|
// 规模小于目标城市,则政府拒绝修建
|
|||
|
continue;
|
|||
|
}
|
|||
|
else if (start_alpha == target_alpha) {
|
|||
|
// 若两个城市规模相等,则修建过后两座城市形成的 league 城市规模系数α增一
|
|||
|
graph->increase_alpha(start);
|
|||
|
}
|
|||
|
else if (start_alpha > target_alpha) {
|
|||
|
// 若大于目标城市,则同意修建,规模系数不变
|
|||
|
;
|
|||
|
}
|
|||
|
// 修建公路,即在关系矩阵上将相应的行列置为true
|
|||
|
graph->incidence[start][target] = graph->incidence[target][start] = true;
|
|||
|
graph->incidence_had_changed = true; // 保护字段为什么能直接访问?
|
|||
|
// 把目标城市所在联盟合并到起始城市所在联盟中
|
|||
|
graph->merge(start, target);
|
|||
|
}
|
|||
|
}
|
|||
|
|
|||
|
int main() {
|
|||
|
int n, beta;
|
|||
|
|
|||
|
std::cout << "输入城市的个数:";
|
|||
|
std::cin >> n;
|
|||
|
auto graph = ComplexGraph(n);
|
|||
|
std::cout << "初始的城市规模为:" << std::endl;
|
|||
|
graph.print_alpha();
|
|||
|
std::cout << "请输入限定系数beta:";
|
|||
|
std::cin >> beta;
|
|||
|
graph.set_beta(beta);
|
|||
|
|
|||
|
std::cout << "初始的距离的邻接矩阵为:" << std::endl;
|
|||
|
graph.print_adjacency();
|
|||
|
|
|||
|
for (int turn_num = 1; ; turn_num++) {
|
|||
|
graph.start_record_incidence();
|
|||
|
one_turn(&graph);
|
|||
|
// 当关系矩阵不再被改变,也就是说明不再修桥了,则说明达到稳定
|
|||
|
if (!graph.stop_record_incidence()) {
|
|||
|
break;
|
|||
|
}
|
|||
|
std::cout << "第" << turn_num << "轮后的关系矩阵如下:" << std::endl;
|
|||
|
graph.print_incidence();
|
|||
|
std::cout << "规模系数如下:" << std::endl;
|
|||
|
graph.print_alpha();
|
|||
|
std::cout << "并查集如下:" << std::endl;
|
|||
|
graph.print_merge_find_set();
|
|||
|
std::cout << std::endl;
|
|||
|
}
|
|||
|
std::cout << "已经达到稳定" << std::endl;
|
|||
|
return 0;
|
|||
|
}
|
|||
|
|
|||
|
// 输入城市的个数:10
|
|||
|
// 初始的城市规模为:
|
|||
|
// 城市联盟 { 0 } 的规模系数为 2
|
|||
|
// 城市联盟 { 1 } 的规模系数为 5
|
|||
|
// 城市联盟 { 2 } 的规模系数为 2
|
|||
|
// 城市联盟 { 3 } 的规模系数为 1
|
|||
|
// 城市联盟 { 4 } 的规模系数为 3
|
|||
|
// 城市联盟 { 5 } 的规模系数为 4
|
|||
|
// 城市联盟 { 6 } 的规模系数为 2
|
|||
|
// 城市联盟 { 7 } 的规模系数为 2
|
|||
|
// 城市联盟 { 8 } 的规模系数为 4
|
|||
|
// 城市联盟 { 9 } 的规模系数为 3
|
|||
|
// 请输入限定系数beta:5
|
|||
|
// 初始的距离的邻接矩阵为:
|
|||
|
// 2147483647 63 39 34 97 93 35 42 68 29
|
|||
|
// 63 2147483647 11 100 82 48 31 2 33 58
|
|||
|
// 39 11 2147483647 85 100 27 47 97 86 91
|
|||
|
// 34 100 85 2147483647 15 32 16 77 84 29
|
|||
|
// 97 82 100 15 2147483647 4 53 63 54 29
|
|||
|
// 93 48 27 32 4 2147483647 25 85 86 58
|
|||
|
// 35 31 47 16 53 25 2147483647 97 27 88
|
|||
|
// 42 2 97 77 63 85 97 2147483647 61 91
|
|||
|
// 68 33 86 84 54 86 27 61 2147483647 66
|
|||
|
// 29 58 91 29 29 58 88 91 66 2147483647
|
|||
|
//
|
|||
|
// 第1轮后的关系矩阵如下:
|
|||
|
// 0 0 0 0 0 0 0 0 0 1
|
|||
|
// 0 0 0 0 0 0 0 0 0 0
|
|||
|
// 0 0 0 0 0 0 0 0 0 0
|
|||
|
// 0 0 0 0 0 0 1 0 0 0
|
|||
|
// 0 0 0 0 0 1 0 0 0 0
|
|||
|
// 0 0 0 0 1 0 0 0 0 0
|
|||
|
// 0 0 0 1 0 0 0 0 1 0
|
|||
|
// 0 0 0 0 0 0 0 0 0 0
|
|||
|
// 0 0 0 0 0 0 1 0 0 0
|
|||
|
// 1 0 0 0 0 0 0 0 0 0
|
|||
|
//
|
|||
|
// 规模系数如下:
|
|||
|
// 城市联盟 { 1 } 的规模系数为 5
|
|||
|
// 城市联盟 { 2 } 的规模系数为 2
|
|||
|
// 城市联盟 { 4 5 } 的规模系数为 4
|
|||
|
// 城市联盟 { 7 } 的规模系数为 2
|
|||
|
// 城市联盟 { 3 6 8 } 的规模系数为 4
|
|||
|
// 城市联盟 { 0 9 } 的规模系数为 3
|
|||
|
// 并查集如下:
|
|||
|
// 9 -1 -1 8 5 -1 8 -1 -1 -1
|
|||
|
//
|
|||
|
// 第2轮后的关系矩阵如下:
|
|||
|
// 0 0 0 0 0 0 0 0 0 1
|
|||
|
// 0 0 0 0 0 0 0 0 0 0
|
|||
|
// 0 0 0 0 0 0 0 0 0 0
|
|||
|
// 0 0 0 0 1 0 1 0 0 0
|
|||
|
// 0 0 0 1 0 1 0 0 0 0
|
|||
|
// 0 0 0 0 1 0 0 0 0 0
|
|||
|
// 0 0 0 1 0 0 0 0 1 0
|
|||
|
// 0 0 0 0 0 0 0 0 0 0
|
|||
|
// 0 0 0 0 0 0 1 0 0 0
|
|||
|
// 1 0 0 0 0 0 0 0 0 0
|
|||
|
//
|
|||
|
// 规模系数如下:
|
|||
|
// 城市联盟 { 1 } 的规模系数为 5
|
|||
|
// 城市联盟 { 2 } 的规模系数为 2
|
|||
|
// 城市联盟 { 7 } 的规模系数为 2
|
|||
|
// 城市联盟 { 3 4 5 6 8 } 的规模系数为 5
|
|||
|
// 城市联盟 { 0 9 } 的规模系数为 3
|
|||
|
// 并查集如下:
|
|||
|
// 9 -1 -1 8 8 8 8 -1 -1 -1
|
|||
|
//
|
|||
|
// 已经达到稳定
|