Форум программистов, компьютерный форум, киберфорум
Prolog
Войти
Регистрация
Восстановить пароль
Блоги Сообщество Поиск Заказать работу  
 
Рейтинг 4.78/9: Рейтинг темы: голосов - 9, средняя оценка - 4.78
0 / 0 / 1
Регистрация: 07.11.2012
Сообщений: 38

Алгоритм Прима-Краскала. Не могу полностью разобраться с кодом

04.05.2014, 22:26. Показов 1875. Ответов 6
Метки нет (Все метки)

Студворк — интернет-сервис помощи студентам
Дана плоская страна и в ней n городов. Нужно соединить все города телефонной связью так, чтобы общая длина телефонных линий была минимальной.
Уточнение задачи. В задаче речь идет о телефонной связи, т.е. подразумевается транзитивность связи: если i-й город связан с j-ым, а j-ый с k-ым, то i-й связан с k-ым.
Здесь фактичеки задача на алгоритм Прима-краскала.У меня есть вот такой вот код, но я еще новичок в прологе и не совсем понимаю его. С алгоритмом краскала если что я знаком)

Что именно я напишу рядом с некоторыми строчками кода, помогите пожалуйста разобраться

Prolog
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
domains
  i=integer line=e(i,i,i) l=line*
facts - lines
  e(i,i,i)
predicates
  cycled(line)
  cycled(i,i,i,i)
  ed(i,i,i)
  kraskal(l,l)
  qsort(l,l)
  partition(l,line,l,l)
  append(l,l,l)
  
goal
  L1=[e(1,1,2),e(4,1,3),e(2,2,3),e(3,2,4),e(1,3,4),
  e(5,3,5),e(3,4,5),e(4,5,6),e(2,2,6),e(5,3,7),e(6,5,7),e(7,6,7)],
  qsort(L1,L),
  kraskal(L,LL), 
  write(LL),nl.
  
clauses
  append([],[X|Xs],[X|Zs]):-append([],Xs,Zs).
  append([X|Xs],Ys,[X|Zs]):-append(Xs,Ys,Zs).
  append([],[],[]).
  qsort([X|Xs],Ys):-partition(Xs,X,Ls,Bs),qsort(Ls,Lo),qsort(Bs,Bo),append(Lo,[X|Bo],Ys).  %я не понимаю вот этот вот "абзац" текста, а именно как работает qsort здесь и partition
  qsort([],[]).
  partition([X|Xs],Y,[X|Ls],Bs):-X=e(Xl,_,_),Y=e(Yl,_,_),Xl<=Yl,!,partition(Xs,Y,Ls,Bs).
  partition([X|Xs],Y,Ls,[X|Bs]):-X=e(Xl,_,_),Y=e(Yl,_,_),Xl>Yl,!,partition(Xs,Y,Ls,Bs).
  partition([],_,[],[]).
 
  kraskal([H|L],[H|LL]):-  %и вкратце если можно еще уточните, как работает вот этот абзац здесь на всякий случай)
  not(cycled(H)),
  H=e(Len,V1,V2),
  assert(e(Len,V1,V2)),
  !,kraskal(L,LL).
  kraskal([_|L],LL):-
  !,kraskal(L,LL).
  kraskal([],[]).
  
  ed(P,X,Y):-e(P,X,Y);e(P,Y,X).
  
  cycled(H):-
  H=e(_,I1,I2),
  ed(_,I1,X1),
  ed(_,I2,X2),
  cycled(X1,X2,I1,I2),!.
 
  cycled(I1,I2,I11,I12):-
  ed(_,I1,X1),X1<>I11,X1<>I12,
  ed(_,I2,X2),X2<>I11,X2<>I12,
  cycled(X1,X2,I1,I2),!.
  cycled(I1,I2,I11,I12):-
  ed(_,I1,X1),X1<>I11,X1<>I12,
  cycled(X1,I2,I11,I2),!.
  cycled(I1,I2,I11,I12):-
  ed(_,I2,X2),X2<>I11,X2<>I12,
  cycled(I1,X2,I1,I12),!.
  cycled(X,X,_,_):-!.
0
Programming
Эксперт
39485 / 9562 / 3019
Регистрация: 12.04.2006
Сообщений: 41,671
Блог
04.05.2014, 22:26
Ответы с готовыми решениями:

Алгоритм Прима-Краскала
Вот код, подскажите пожалуйста, какой вопрос вводить для выдачи результата? путь(X,Z,Граф,Res):- маршрут(X,,Граф,Res). ...

Алгоритм Прима / Краскала: Соединить все города телефонной связью
Дана плоская страна и в ней n городов. Нужно соединить все города телефонной связью так, чтобы общая длина телефонных линий была...

Поиск минимального остовного дерева в несвязном графе. Алгоритм Прима-Краскала
Господа. Дело такое - нахожу я минимальное остовное дерево в связном графе (в котором каждая вершина с любой другой). А вот для несвязного...

6
0 / 0 / 1
Регистрация: 07.11.2012
Сообщений: 38
12.05.2014, 16:19  [ТС]
кто нииииибудь, пожалуйста)) очень нужно)
0
Фрилансер
 Аватар для Black Fregat
3709 / 2083 / 567
Регистрация: 31.05.2009
Сообщений: 6,683
13.05.2014, 23:41
По qsort что непонятно? Это известный алгоритм: разбиение, рекурсивная сортировка половинок, слияние
1
0 / 0 / 1
Регистрация: 07.11.2012
Сообщений: 38
23.05.2014, 20:41  [ТС]
Вот не совсем понимаю сам механизм работы. Что он подает в виде Ls,Bs,B0,L0 и как работает partition
0
Фрилансер
 Аватар для Black Fregat
3709 / 2083 / 567
Регистрация: 31.05.2009
Сообщений: 6,683
24.05.2014, 03:13
Prolog
1
2
3
4
5
6
7
8
9
10
% Первый параметр входной - исходный список
% Второй параметр выходной - отсортированный список
 
qsort([X|Xs],Ys):-              % От входного списка сразу отделяем первый элемент
     partition(Xs,X,Ls,Bs),     % Выполняем расщепление на 2 списка по выбранному элементу
                                % При этом в Ls попадают элементы <= X
                                % а в Bs попадают элементы > X
     qsort(Ls,Lo),              % обе половинки рекурсивно сортируем тем же qsort
     qsort(Bs,Bo),              % получаем отсортированные половинки Lo и Bo
     append(Lo,[X|Bo],Ys).      % Формируем выходной список как Lo + [X] + Bo
2
0 / 0 / 1
Регистрация: 07.11.2012
Сообщений: 38
26.05.2014, 19:58  [ТС]
Спасибо большое) а можете еще посмотреть, вот здесб же я правильно рассуждаю:
Prolog
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
cycled(H):-
  H=e(_,I1,I2),
  ed(_,I1,X1),
  ed(_,I2,X2),
  cycled(X1,X2,I1,I2),!.  
 
  cycled(I1,I2,I11,I12):-
  ed(_,I1,X1),X1<>I11,X1<>I12,
  ed(_,I2,X2),X2<>I11,X2<>I12,
  cycled(X1,X2,I1,I2),!.
  cycled(I1,I2,I11,I12):-
  ed(_,I1,X1),X1<>I11,X1<>I12,
  cycled(X1,I2,I11,I2),!.
  cycled(I1,I2,I11,I12):-
  ed(_,I2,X2),X2<>I11,X2<>I12,
  cycled(I1,X2,I1,I12),!.
  cycled(X,X,_,_): -!.
то есть сначала мы грубо говоря придаем значение координатам, где I1 -это начальная точка графа,а I2 -куда приходит ребро. И потом делаем условия которые проверяют наличия зациклинности. Но не совсем понятно что делает ed в следствие чего не могу полностью понять как работает это проверка на цикл.
0
Фрилансер
 Аватар для Black Fregat
3709 / 2083 / 567
Регистрация: 31.05.2009
Сообщений: 6,683
29.05.2014, 19:52
Очень странно написанный фрагмент..
На мой взгляд, тут и название не совсем удачное выбрано, и алгоритм излишне усложнен, и не совсем он правильный.

На самом деле предикат cycled(I1,I2,I11,I12) проверяет, существует ли в текущем дереве путь между вершинами I1 и I2.
Вершины I11 и I12 - это предыдущие вершины на искомом пути, они передаются в предикат, чтобы тот не зацикливался:
каждый раз проверяем, что назад шагать нельзя.

Prolog
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
% Шагаем с двух концов сразу
  cycled(I1,I2,I11,I12):-
 ed(_,I1,X1),X1<>I11,X1<>I12, % один шаг от первой вершины, но не назад  
 ed(_,I2,X2),X2<>I11,X2<>I12, % один шаг от второй вершины, но не назад
 cycled(X1,X2,I1,I2),!.       % рекурсивно продолжаем поиск
 
% Шагаем с одного конца
 cycled(I1,I2,I11,I12):-
 ed(_,I1,X1),X1<>I11,X1<>I12, % один шаг от первой вершины, но не назад
 cycled(X1,I2,I11,I2),!.      % рекурсивно продолжаем поиск
 
% Шагаем с другого конца
 cycled(I1,I2,I11,I12):-
 ed(_,I2,X2),X2<>I11,X2<>I12, % один шаг от второй вершины, но не назад
 cycled(I1,X2,I1,I12),!.      % рекурсивно продолжаем поиск
 
% А это правило надо бы поставить первым - иначе оно даже в очевидном случае
% будет пытаться мотать варианты по всему дереву, пока перебор не выдохнется..
  cycled(X,X,_,_): -!.         % выход из рекурсии при совпадении вершин
Половина проверок в приведенном коде - избыточные.
Они добавлены только из=за неправильного порядка предикатов

Насчет предиката ed - он всего лишь симметрически замыкает e, как видно из строчки
Prolog
1
ed(P,X,Y):-e(P,X,Y);e(P,Y,X).
То есть он избавляет от необходимости хранить сразу два ребра - в прямом и обратном направлении

Может показаться, что попытка шагать с двух концов сразу ускорит решение.
Но это не так. Если оставить шаг только с одного конца, будет и проще, и быстрее:
Prolog
1
2
3
4
5
path(From, From, _):-!.
path(From, To, OldFrom):-
  ed(_, From, NewFrom), 
  NewFrom <> OldFrom, 
  path(NewFrom, To, From).
0
Надоела реклама? Зарегистрируйтесь и она исчезнет полностью.
inter-admin
Эксперт
29715 / 6470 / 2152
Регистрация: 06.03.2009
Сообщений: 28,500
Блог
29.05.2014, 19:52
Помогаю со студенческими работами здесь

Неясность в алгоритме Прима-Краскала
Изучаю алгоритм Прима-Краскала и не понимаю одну строчку (выделена комментарием). Привожу отрывки из кода: type rebro = record ...

Задача Прима-Краскала с граф интерфейсом
Задача Прима-Краскала + нужен минимальный графический интерфейс

Задача Прима-Краскала (SWI-Prolog)
Дана страна (плоская и в ней n городов). Нужно соединить города телефонной линией, чтобы ее общая длина была минимальной. Решение задачи...

Не могу разобраться разобраться с кодом меню
Добрый день. Я понимаю, что тут все, наверное, элементарно. Но я только начала изучение js и пока для меня все страшно и сложно. Проблема...

Найти минимальное остовное дерево с помощью алгоритмов Прима и Краскала.
Найти минимальное остовное дерево с помощью алгоритмов Прима и Краскала для графа,заданного матрицей весов


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
7
Ответ Создать тему
Новые блоги и статьи
SDL3 для Web (WebAssembly): Реализация движения на Box2D v3 - трение и коллизии с повёрнутыми стенами
8Observer8 20.02.2026
Содержание блога Box2D позволяет легко создать главного героя, который не проходит сквозь стены и перемещается с заданным трением о препятствия, которые можно располагать под углом, как верхнее. . .
Конвертировать закладки radiotray-ng в m3u-плейлист
damix 19.02.2026
Это можно сделать скриптом для PowerShell. Использование . \СonvertRadiotrayToM3U. ps1 <path_to_bookmarks. json> Рядом с файлом bookmarks. json появится файл bookmarks. m3u с результатом. # Check if. . .
Семь CDC на одном интерфейсе: 5 U[S]ARTов, 1 CAN и 1 SSI
Eddy_Em 18.02.2026
Постепенно допиливаю свою "многоинтерфейсную плату". Выглядит вот так: https:/ / www. cyberforum. ru/ blog_attachment. php?attachmentid=11617&stc=1&d=1771445347 Основана на STM32F303RBT6. На борту пять. . .
Камера Toupcam IUA500KMA
Eddy_Em 12.02.2026
Т. к. у всяких "хикроботов" слишком уж мелкий пиксель, для подсмотра в ESPriF они вообще плохо годятся: уже 14 величину можно рассмотреть еле-еле лишь на экспозициях под 3 секунды (а то и больше),. . .
И ясному Солнцу
zbw 12.02.2026
И ясному Солнцу, и светлой Луне. В мире покоя нет и люди не могут жить в тишине. А жить им немного лет.
«Знание-Сила»
zbw 12.02.2026
«Знание-Сила» «Время-Деньги» «Деньги -Пуля»
SDL3 для Web (WebAssembly): Подключение Box2D v3, физика и отрисовка коллайдеров
8Observer8 12.02.2026
Содержание блога Box2D - это библиотека для 2D физики для анимаций и игр. С её помощью можно определять были ли коллизии между конкретными объектами и вызывать обработчики событий столкновения. . . .
SDL3 для Web (WebAssembly): Загрузка PNG с прозрачным фоном с помощью SDL_LoadPNG (без SDL3_image)
8Observer8 11.02.2026
Содержание блога Библиотека SDL3 содержит встроенные инструменты для базовой работы с изображениями - без использования библиотеки SDL3_image. Пошагово создадим проект для загрузки изображения. . .
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin
Copyright ©2000 - 2026, CyberForum.ru