Добавил:
Опубликованный материал нарушает ваши авторские права? Сообщите нам.
Вуз: Предмет: Файл:

Лабораторная работа №2

.DOC
Скачиваний:
34
Добавлен:
02.05.2014
Размер:
59.9 Кб
Скачать

Лабораторная работа N 2

Тема:

Алгоритм прохода графа в глубину и в ширину.

Цель работы:

Изучение алгоритмов поиска в графе, а также различных форм организации хранения и обработки данных. Разработка программы, реализующей алгоритм поиска в глубину. Изучение алгоритмов поиска в графе. Разработка программы, выполняющей поиск в ширину.

Структуры данных:

тип списков -

Каждый тип списков определяет множество конечных последовательностей элементов, имеющий заданный базисный тип. Число элементов списка, называемое его длиной, в разных списках одного типа может быть различным. Список, не имеющий элементов, называется пустым.

Для списка определены понятия начального, конечного и текущего элементов, а также следующего и предыдущего элементов по отношению к текущему. Текущий элемент- это тот единственный элемент списка, который в данный доступен для обработки.

Тип очередей -

Очередь используется для реализации такой дисциплины обработки элементов списка, при которой элементы списка удаляются из него в порядке их включения в список (т.е. по принципу "Первым пришел - первым ушел").

Набор базисных операций над списками, являющимися очередями, состоит из четырех операций:

1)Создание пустой очереди;

2)Проверка очереди на пустоту;

3)Выборки первого элемента из очереди с одновременным его удалением;

4) Занесения некоторого значения базисного типа в качестве нового последнего элемента очереди.

Тип стеков -

Стек используется для реализации такой дисциплины обработки элементов списка, при которой элементы списка удаляются из него в порядке, обратном порядку их занесения в стек (т.е. по принципу "Последним пришел – первым ушел").

Набор базисных операций над списками, являющимися стеками, состоит из пяти операций:

1) Создание пустого стека;

2) Проверка стека на пустоту;

3,4) Выборки последнего элемента из стека без удаления его из стека или с его удалением;

5) Занесения некоторого значения базисного типа в качестве нового последнего элемента стека.

Тип деревьев -

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

Дерево, в котором список поддеревьев пуст, называется тривиальным, а корень тривиального дерева - листом дерева. Корень дерева называется отцом вершин, являющихся корнями поддревьев; а эти вершины называются сыновьями корня дерева, причем корень первого поддерева является старшим сыном, а корень каждого следующего поддерева в списке называется братом корня предыдущего поддерева.

Набор базисных операций для деревьев состоит из следующих операций: Создание тривиального дерева по элементу базисного типа и выборки или замены корня дерева или списка его поддеревьев, а также всех операций (для списка поддеревьев), которые являются базисными для списка.

Обход графа в глубину -

При обходе дерева в глубину (известном также как прохождение в прямом порядке) вершины дерева посещаются в соответствии со следующей рекурсивной процедурой: сначала посетить корень дерева q; затем если корень рассматриваемого дерева не является листом, то для каждого сына p корня q рекурсивно обратиться к процедуре обхода в глубину для того, чтобы обойти все поддеревья с корнями p в порядке упорядоченности вершин p как сыновей корня q.

Алгоритм поиска в ширину -

Обход графа в ширину, как и обход в глубину должен обеспечивать днократное посещение каждой вершины графа, только по другому принципу. После посещения исходной вершины, из которой начинается поиск, посещаются все вершины, смежные с данной, затем, все вершины, смежные с этими вершинами и т.д., пока не будут посещены все вершины графа. Очевидно, что для этого необходимо, чтобы заданный граф был связанным.

Способ обхода дерева в ширину, называемый иногда способом прохождения в горизонтальном порядке, осуществляет посещение вершин дерева слева направо, уровень за уровнем вниз от корня.

Текст программы на языке C.

#include<stdio.h>

#include<conio.h>

#include<stdlib.h>

struct gr //сруктура для списка смежности

{int num;

int ind;

struct gr *next;

};

typedef struct gr graf; //преобразование типа для удобства

graf *start,*current,**mas;

void inputss(void);

void shiri(int);

void nulind(void);

void glub(int);

int a,n=0,*masg;

void main()

{

int i,d;

clrscr();

inputss();

printf("\nvvedite koreni ");

scanf(" %d",&d);

shiri(d);

nulind();

masg=(int*)malloc(a*sizeof(int));

n=0;

masg[n]=d;

mas[d-1]->ind=1;

n=1;

glub(d);

printf("\nobhod v glubinu\n");

for(i=0;i<a;i++)

printf(" %d",masg[i]);

getch();

}

void inputss(void) //процедура ввода списка смежности

{

int i,d;

d=0;

printf ("Vvedite razmernosti massiva\nko-lvo versin ");

scanf (" %d",&a);

mas=(graf**)malloc(a*sizeof(current));

for (i=0;i<a;i++)//форматированнай ввод списка, ввод строки до 0

{ //0 вводится как отметки конца строки главной вершины

printf("versina %d- ",i+1);

if (d==0) {current=(graf*)malloc(sizeof(graf));

start=current; d=1;} //создание начала списка или прдолжения списка

else {current->next=(graf*)malloc(sizeof(graf));

current=current->next;};

current->num=i+1;

mas[n]=current;n++;

current->ind=0;

do{

current->next=(graf*)malloc(sizeof(graf));

current=current->next;scanf(" %d",&current->num);

} while (current->num!=0);

}

current->next=NULL; //ссылка на NULL последнего элемента списка

};

void shiri(int d)

{int i,ind=1,n=1;

mas[d-1]->ind=n;

n++;

while(ind==1)

{ind=0;

for(i=0;i<a;i++)

{if(mas[i]->ind==n-1)

{current=mas[i]->next;

while (current->num!=0)

{if(mas[current->num-1]->ind==0)

{mas[current->num-1]->ind=n;

ind=1;}

current=current->next;}

}

}

n++;

}

ind=1;

n=1;

printf("obhod v shirinu\n");

while(ind==1)

{ind=0;

for(i=0;i<a;i++)

{if (mas[i]->ind==n) {printf("%d ",mas[i]->num);ind=1;}

}

n++;

printf("\n");

};

};

void nulind (void)

{current=start;

while (current!=NULL)

{current->ind=0;

current=current->next;

}

};

void glub (int d)

{graf *current1;

current1=mas[d-1]->next;

while (current1->num!=0)

{if (mas[current1->num-1]->ind==0)

{ masg[n]=current1->num;n++;

mas[current1->num-1]->ind=1;

glub(current1->num);

};

current1=current1->next;

};

};

Пример дерева и его представления.

Обход в глубину: 1,2,5,6,3,7,4,8,9.

Обход в ширину: 1,2,3,4,5,67,8,9.

Вывод: Программа позволяет осуществлять проход графа и дерева в глубину и ширину, следовательно выполняет все поставленные перед ней задачи.

5