#define _CRT_SECURE_NO_WARNINGS #include #include #include /* O(n^2), n - количество вершин, используем матрицу смежности */ void solve(int **adj, int **res, int n); int main() { int n; scanf("%d", &n); int **adj = (int**)calloc(n, sizeof(int*)); for (int i = 0; i < n; i++) { adj[i] = (int*)calloc(n, sizeof(int)); } for (int i = 0; i < n; i++) { for (int j = 0; j < n; j++) { scanf("%d", &adj[i][j]); } } int **res = (int**)calloc(n, sizeof(int*)); for (int i = 0; i < n; i++) { res[i] = (int*)calloc(n, sizeof(int)); } solve(adj, res, n); printf("Решение:\n"); for (int i = 0; i < n; i++) { for (int j = i + 1; j < n; j++) { if (res[i][j] != 0) { printf("%i-%i: %i\n", i, j, res[i][j]); } } } /* Освобождаем память */ for (int i = 0; i < n; i++) { free(adj[i]); } free(adj); for (int i = 0; i < n; i++) { free(res[i]); } free(res); } void solve(int **adj, int **res, int n) { /* Множество выбранных вершин, 1 - выбрано, 0 - не выбрано */ int* set = (int *)calloc(n, sizeof(int)); /* Выбрали первую вершину */ set[0] = 1; /* Количество выбранных вершин */ int set_size = 1; while (set_size != n) { /* "Бесконечность" */ int min = INT_MAX; /* Номер вершины */ int k_i; int k_j; for (int i = 0; i < n; i++) { /* Если вершина еще не выбрана, то пропускаем её */ if (!set[i]) { continue; } /* Рассматриваем выбранные вешины */ for (int j = 0; j < n; j++) { /* Если вершина k_j выбрана, то пропускаем её, она уже в компоненте связности */ if (set[j] == 1) { continue; } /* Выбираем кратчайшее ребро */ if (min > adj[i][j] && adj[i][j]) { min = adj[i][j]; k_i = i; k_j = j; } } } /* Добавляем вершину k_j в компоненту связности */ set[k_j] = 1; /* Сохраняем в симметрическую матрицу результат */ res[k_i][k_j] = adj[k_i][k_j]; res[k_j][k_i] = adj[k_i][k_j]; set_size++; } free(set); }