用c语言编写程序,输入一个简单有向图的邻接矩阵,输出该有向图的强分图,单侧分图和r
时间: 2024-03-18 15:38:57 浏览: 64
数据结构-c语言-带main函数-图7.2-图的存储结构-图的邻接矩阵的创建-有向图。
5星 · 资源好评率100%
这道题目与你之前提出的问题有所不同。这里需要输出强分图、单侧分图和弱分图的连通分量,而不是输出它们的邻接矩阵。下面是我的回答:
```c
#include <stdio.h>
#define MAX_VERTEX_NUM 100 // 最大顶点数
typedef int AdjMatrix[MAX_VERTEX_NUM][MAX_VERTEX_NUM]; // 邻接矩阵类型
void input_graph(AdjMatrix G, int n) {
printf("请输入邻接矩阵:\n");
for (int i = 0; i < n; i++) {
for (int j = 0; j < n; j++) {
scanf("%d", &G[i][j]);
}
}
}
void output_graph(int C[], int n) {
printf("连通分量为:\n");
for (int i = 0; i < n; i++) {
if (C[i] == -1) {
continue;
}
printf("%d ", i);
for (int j = i + 1; j < n; j++) {
if (C[j] == C[i]) {
printf("%d ", j);
C[j] = -1;
}
}
printf("\n");
}
}
void strong_graph(AdjMatrix G, int n) {
int num = 0;
int C[MAX_VERTEX_NUM] = {-1};
int DFN[MAX_VERTEX_NUM] = {0};
int LOW[MAX_VERTEX_NUM] = {0};
int inStack[MAX_VERTEX_NUM] = {0};
int stack[MAX_VERTEX_NUM] = {0};
int top = -1;
// 强连通分量 Tarjan 算法
for (int i = 0; i < n; i++) {
if (DFN[i] == 0) {
top++;
stack[top] = i;
DFN[i] = LOW[i] = ++num;
inStack[i] = 1;
for (int j = 0; j < n; j++) {
if (G[i][j] == 1) {
if (DFN[j] == 0) {
top++;
stack[top] = j;
DFN[j] = LOW[j] = ++num;
inStack[j] = 1;
}
if (inStack[j]) {
if (LOW[i] > DFN[j]) {
LOW[i] = DFN[j];
}
}
else {
strong_graph(G, j, num, C, DFN, LOW, inStack, stack, top);
if (LOW[i] > LOW[j]) {
LOW[i] = LOW[j];
}
}
}
}
if (DFN[i] == LOW[i]) {
int j;
do {
j = stack[top--];
inStack[j] = 0;
C[j] = i;
} while (j != i);
}
}
}
output_graph(C, n);
}
void one_side_graph(AdjMatrix G, int n) {
int visited[MAX_VERTEX_NUM] = {0};
int C[MAX_VERTEX_NUM] = {-1};
int num = 0;
for (int i = 0; i < n; i++) {
if (!visited[i]) {
C[i] = num;
visited[i] = 1;
for (int j = i + 1; j < n; j++) {
if (G[i][j] && G[j][i]) {
C[j] = num;
visited[j] = 1;
}
}
num++;
}
}
output_graph(C, n);
}
void weak_graph(AdjMatrix G, int n) {
int visited[MAX_VERTEX_NUM] = {0};
int C[MAX_VERTEX_NUM] = {-1};
int num = 0;
for (int i = 0; i < n; i++) {
if (!visited[i]) {
C[i] = num;
visited[i] = 1;
for (int j = i + 1; j < n; j++) {
if (G[i][j] || G[j][i]) {
C[j] = num;
visited[j] = 1;
}
}
num++;
}
}
output_graph(C, n);
}
int main() {
int n;
AdjMatrix G;
printf("请输入顶点数:");
scanf("%d", &n);
input_graph(G, n);
strong_graph(G, n);
one_side_graph(G, n);
weak_graph(G, n);
return 0;
}
```
程序中,我们定义了邻接矩阵类型 `AdjMatrix`,并实现了输入邻接矩阵的函数。`strong_graph` 函数计算强分图的连通分量,并输出结果;`one_side_graph` 函数计算单侧分图的连通分量,并输出结果;`weak_graph` 函数计算弱分图的连通分量,并输出结果。强连通分量的算法采用经典的 Tarjan 算法。
阅读全文