AiSD Wyklad11 dzienne id 53494 Nieznany

background image

Algorytmy z powrotami

Algorytmy z powrotami są wykorzystywane do rozwiązywania
problemów, w których z określonego zbioru jest wybierana sekwencja
obiektów tak, aby spełniała ona określone kryteria.


Klasycznym przykładem jest rozwiązanie problemu n-królowych.
Zadaniem jest ustawienie n-królowych na szachownicy n

×

n w taki

sposób, aby się wzajemnie nie szachowały.
Sekwencją w tym problemie jest n pozycji, na których są umieszczone
królowe, zbiorem dla każdego wyboru jest n

2

możliwych pól na

szachownicy. Kryterium jest takie, że królowe nie mogą się
wzajemnie szachować.

Algorytmy z powrotami są zmodyfikowanym przeszukiwaniem
drzewa ( z korzeniem ) w głąb. Na początku odwiedzamy korzeń, a
poźniej po przejściu do węzła przeglądane są wszystkie węzły
potomne.

Generalnie przeszukiwanie nie wymaga określonego porządku
odwiedzania węzłów, ale wygodniej jest gdy przeszukiwane są węzły
od lewej do prawej.

Przykład przeszukiwania drzewa w głąb z węzłami ponumerowanymi
w kolejności ich odwiedzania:

background image

Węzły są ponumerowane w kolejności ich odwiedzania. Jak widać
podczas wyszukiwania w głąb przechodzi się po ścieżce tak głęboko,
jak jest to możliwe, aż do osiągnięcia ślepego zaułka. Następnie
wracamy do węzła z niodwiedzonymi węzłami potomnymi i znów
przechodzimy w głąb tak daleko, jak jest to możliwe.

Rozważmy ustawienie 4 królowych na szachownicy 4

× 4.


Problem można rozwiązać przez ustawienie królowych w kolejnych
wierszach i sprawdzanie, która kombinacja kolumn daje prawidłowe
rozwiązanie. Daje to 4

× 4 × 4 × 4 = 256 potencjalnych rozwiazań.


Można tworzyć potencjalne rozwiązania przez tworzenie drzewa:
w węzłach drzewa z poziomu 1 będą zapisane kolumny wybrane dla
pierwszej królowej, w węzłach poziomu 2 wybrane kolumny dla
drugiej królowej, etc.

Ścieżka od węzła głównego do liścia jest potencjalnym rozwiazaniem.
Liść to jest węzeł bez węzłów potomnych. Drzewo takie nazywamy
drzewem przestrzeni stanów.

Fragment drzewa przestrzeni stanów pokazano poniżej:

background image

Całe drzewo ma 256 liści, po jednym dla każdego potencjalnego
rozwiązania. W każdym węźle przechowywana jest para liczb <i,j>,
oznaczająca, że królowa z wiersza i jest umieszczona w kolumnie j.

Aby określić rozwiązanie, węzły są odwiedzane zgodnie z metodą
przeszukiwania w głąb, w którym węzły pochodne są odwiedzane od
strony lewej do prawej.

Pierwsze sprawdzane scieżki to:
[<1.1><2.1><3.1><4.1>]
[<1.1><2.1><3.1><4.2>]
[<1.1><2.1><3.1><4.3>]
[<1.1><2.1><3.1><4.4>]
[<1.1><2.1><3.2><4.1>]

Algorytm z powrotami jest algorytmem, w którym po zorientowaniu
się, że węzeł prowadzi do ślepego zaułka, wracamy do węzła
nadrzędnego i kontynuujemy wyszukiwanie od następnego węzła.


Węzeł nazywamy nieobiecującym, gdy w czasie jego odwiedzania
można określić, że nie może on doprowadzić do rozwiązania
(przykład poniżej).

W przeciwnym razie węzeł jest nazywany obiecującym.

Algorytm z powrotami polega na wykonywaniu przeszukiwania w
głąb drzewa przestrzeni stanów, aby sprawdzić czy węzeł jest
obiecujący, czy nie. Jeżeli węzeł nie jest obiecujący, wracamy do
węzła nadrzędnego.

background image

Ogólny algorytm z powrotami:

void checknode (node v)

{

node u;

if (promising(v))
if(istnieje rozwiązanie dla v)

drukuj rozwiązanie;

else

for(każdy węzeł pochodny u węzła v)

checknode(u);

}

Algorytm z powrotami jest identyczny jak przeszukiwanie w głąb,
poza tym, że węzły pochodne są odwiedzane tylko w przypadku, gdy
węzeł macierzysty jest obiecujący i nie znaleziono w nim rozwiązania

Dla problemu n-królowych funkcja promising zwraca false , jeżeli
węzeł i dowolny z jego przodków oznaczają umieszczenie królowej w
tej samej kolumnie lub przekątnej (oznaczenie x na rys.).

background image



Algorytm z powrotami sprawdza 27 węzłów w celu odszukania
rozwiązania, bez zastosowania tego algorytmu trzeba sprawdzić 155
wezłów w celu odszukania tego samego rozwiązania.

Nieefektywność w ogólnym algorytmie z powrotami (procedura
checknode) wynika z faktu, że sprawdzamy czy węzeł jest obiecujący,
po przekazaniu go do procedury. Rekordy aktywacji wezłów
nieobiecujących są niepotrzebnie odkładane na stos rekordów
aktywacji.


Algorytm ze sprawdzeniem czy wezeł jest obiecujący, przed
wywołaniem rekurencyjnym, wyglądałby następujaco:


background image


void expand (node v)
{

node u;

for (każdy węzeł pochodny u węzła v)

if (promising(u))

if (istnieje rozwiazanie dla u)

drukuj rozwiazanie;

else

expand(u);

}


Wersja poprzednia jest łatwiejsza do zrozumienia, gdyż wszystkie
operacje są wykonywane w checknode tzn. : sprawdzanie czy węzeł
jest obiecujący; jeżeli jest obiecujący to czy zawiera rozwiązanie;
drukowanie rozwiązania.

Problem n-królowych



Funkcja sprawdzająca, czy węzeł jest obiecujący, musi sprawdzać, czy
dwie królowe są w tej samej kolumnie lub na tej samej przekątnej.

Sprawdzenie kolumny to:
col(i) = col(k)

gdzie col(i) jest kolumną w której jest umieszczona królowa z i-tego
wiersza.

Sprawdzenie przekątnej to:

col(i) - col(k) = i k lub col(i) - col(k) = k i



background image

Przykładowo:

col(6) – col(3) = 4-1 = 3 = 6-3

col(6) – col(2) = 4-8 = -4 = 2-6


Algorytm z powrotami dla problemu n-królowych

Problem: umieść n królowych na szachownicy w taki sposób, żeby
żadne dwie królowe nie znalazły się w tym samym wierszu, tej samej
kolumnie oraz na tych samych przekątnych.

Dane wejściowe: dodatnia liczba całkowita n.

Wynik: wszystkie możliwe sposoby na umieszczenie n królowych na
szachownicy n

×

n tak, aby się wzajemnie nie szachowały. Każdy

wynik cząstkowy składa się z tablicy liczb całkowitych col,
indeksowanych od 1 do n, gdzie col(i) jest kolumną, w której
umieszczona została królowa z wiersza i.


background image

void queens (index i)

{

index j;

if (promising(i) )

if(i= = n)

cout<< od col[i] do col[n];

else
for(j=1;j<=n;j++){//Sprawdzenie czy królow

col[i+1] = j; //w i+1-tym wierszu moze

queens(i+1); //byc ustawiona w kazdej

//z n kolumn

}

}

bool promising (index i)

{

index k;

bool switch;


k=1;

switch = true; //Sprawdź czy jakas

//krolowa szachuje królową

while(k<i && switch){ //w i-tym wierszu

if(col[i]==col[k] || abs(col[i]-col[k])==i-k)

switch = false;

k++;

}

return switch;

}

Algorytm powyższy tworzy wszystkie rozwiązania problemu n-
królowych. Przerobienie programu tak, aby zatrzymywał się po
znalezieniu pierwszego rozwiazania, jest proste.

W analizie algorytmu należy określić ilość sprawdzonych węzłów
jako funkcję wartości n, czyli liczby królowych. Górną granicę liczby
węzłów w drzewie przestrzeni stanów można dośc łatwo policzyć.

background image

Drzewo zawiera 1 węzeł na poziomie 0, n węzłów na poziomie 1, n

2

węzłów na poziomie 2 oraz n

n

na poziomie n.

Całkowita liczba węzłów wynosi

1+n+n

2

+n

3

+…+n

n

= (n

n+1

– 1) / (n – 1)


Przykladowo, dla n=8 mamy

(8

8+1

– 1) / (8 – 1) = 19 173 961 węzłów


Analiza ta jest nie w pełni użyteczna bo zadaniem algorytmu z
powrotami jest uniknięcie sprawdzania wielu z tych węzłów.

Można również określić górną granicę ilości węzłów obiecujących
(dla n=8). Pierwsza królowa może być umieszczona w dowolnej z
ośmiu kolumn, druga może być umieszczona w jednej z siedmiu
kolumn. Po ustawieniu drugiej królowej dla trzeciej zostanie do
wyboru sześć kolumn. Dlatego mamy co najwyżej:

1 + 8 + 8

×7 + 8×7×6 + 8×7×6×5 + … + 8! = 109 601

obiecujących węzłów.

Ogólnie dla dowolnego n mamy co nawyżej

1 + n + n(n-1) + n(n-1)(n-2) + … + n! obiecujących węzłów.

Analiza ta nie jest pełna, gdyż po pierwsze nie bierze pod uwagę
sprawdzania przekątnych, po drugie całkowita liczba odwiedzanych
węzłów zawiera zarówno węzły obiecujące, jak i nieobiecujące.

Najprostszą metodą byloby uruchomienie programu na komputerze i
zliczanie odwiedzanych węzłów.




background image


n Algorytm A Algorytm B Algorytm z powrotami
________________________________________________________________
Liczba węzłów Liczba potencjalnych Liczba węzłów Liczba
sprawdzanych rozwiązań n! sprawdzanych znalezionych
(bez powrotów) (rozne kolumny) (z powrotami) węzłów obiec.
________________________________________________________________
4 341 24 61 17

8 19 173 961 40 320 15 721 2057

12 9.73

×10

12

4.79

×10

8

1.01

×10

7

8.56

×10

5


14 1.20

×10

16

8.72

×10

10

3.78

×10

8

2.74

×10

7


Oczywiście, uruchamianie algorytmu w celu określenia jego
efektywności nie jest faktyczną analizą. Zadaniem analizy jest
określenie jak efektywny jest algorytm, jeszcze przed jego
uruchomieniem.

Co można zrobić w takiej sytuacji ?

Algorytmy Monte-Carlo

Drzewa przestrzeni stanów dla algorytmów z powrotami mają
wykładniczo lub szybciej roznąca liczbę węzłów. Warto zauważyć, że
jeśli mamy dwa przypadki z taką samą wartością n, jeden z nich może
wymagać sprawdzenia kilku węzłów, natomiast inne wymagają
sprawdzenia całego drzewa przestrzeni stanów.
Jeżeli oszacujemy, jak efektywny jest dany algorytm z powrotami dla
danego przypadku, możemy zdecydować, czy zastosowanie go jest
sensowne.

Algorytm Monte-Carlo to algorytm probabilistyczny. Jest to taki
algorytm, w którym następna wykonywana instrukcja jest czasami
określana w sposób losowy, zgodnie z pewnym rozkładem losowym.

background image

Algorytm deterministyczny to taki, w którym przedstawiony
przypadek nie może mieć miejsca.
Algorytm Monte-Carlo pozwala oszacować spodziewaną wartość
zmiennej losowej, zdefiniowanej w przestrzeni próbek, na podstawie
średniej wartości losowych próbek z tej przestrzeni. Nie ma
gwarancji, że to oszacowanie jest bliskie właściwej wartości
oczekiwanej, ale prawdopodobieństwo, że jest bliskie, zwiększa się ze
wzrostem czasu działania algorytmu (ilosci uruchomień algorytmu).

Jak wykorzystać algorytm Monte-Carlo do oszacowania efektywności
algorytmu z powrotami ?

Generujemy w drzewie „typową ścieżkę”, składajacą się z węzłów,
które powinny być sprawdzone w danym przypadku, a nastepnie
szacujemy liczbę węzłów, odgałęziających się od tej ścieżki.
Oszacowanie to daje w wyniku szacunkową liczbę węzłów, które
należy sprawdzić w celu znalezienia wszystkich rozwiązań. Inaczej
mówiąc, jest to szacunkowa liczba węzłów w przeciętnym drzewie
stanów.

Muszą być spełnione dwa warunki:

• we wszystkich węzłach na tym samym poziomie drzewa

przestrzeni stanów powinna być używana ta sama funkcja
określająca, czy węzeł jest obiecujący

• węzły na tym samym poziomie w drzewie przestrzeni stanów

muszą mieć taka samą liczbę potomków.


Algorytm dla n-królowych spełnia te warunki.

Technika Monte-Carlo wymaga losowego generowania obiecującego
potomka węzła, zgodnie z rozkładem normalnym, czyli generowania
liczb losowych.

Sposób realizacji:

• niech m

0

będzie liczbą obiecujących potomków korzenia

• losowo generujemy obiecujący węzeł pochodny na poziomie 1.

Niech m

1

będzie liczbą obiecujących potomków tego węzła.

background image

• losowo wygeneruj obiecujący węzeł dla węzła uzyskanego w

poprzednim kroku. Niech m

2

będzie liczbą obiecujących

potomków tego węzła.
……

• Losowo wygeneruj obiecujący węzeł dla węzła uzyskanego w

poprzednim kroku. Niech m

i

będzie liczbą obiecujących

potomków tego węzła.


Proces jest kontynuowany, dopóki nie zostaną znalezione żadne
obiecujące węzły potomne. m

i

jest szacunkową średnią liczbą

obiecujących węzłów na poziomie i.
Niech t

i

= całkowita liczba potomków węzła na poziomie i


Wszystkie t

i

węzłów zostaje sprawdzone i tylko m

i

obiecujacych

węzłów potomnych ma sprawdzone węzły potomne. Szacunkowa
liczba węzłów sprawdzonych przez algorytm z powrotami w celu
wyszukania wszystkich rozwiązań wynosi

1+ t

0

+ m

0

t

1

+ m

0

m

1

t

2

+ m

0

m

1

…m

i-1

t

i

+ ..

.

Ogólny algorytm obliczający tą średnią może wygladać następująco
( mprod = m

0

m

1

…m

i-1

) .



Szacowanie Monte-Carlo

Problem: oszacuj efektywność algorytmu z powrotami, korzystając z
algorytmu Monte Carlo.

Dane wejściowe: problem rozwiazywany przez algorytm z
powrotami.

Wynik: szacunkowa liczba węzłów w przyciętym drzewie przestrzeni
stanów generowanych przez algorytm, który jest liczbą węzłów, jaką
musi sprawdzić algorytm w celu znalezienia wszystkich rozwiązań
danego przypadku.

background image




int estimate ()

{

node v;

int m,mprod,t,numnodes;

v = korzeń drzewa stanów;

numnodes = 1;

m=1;

mprod=1;
while

(m!=0) {

t=liczba potomków v;

mprod=mprod*m;

numnodes=numnodes+mprod*t;

m=liczba obiecujacych potomków v;
if

(m!=0)

v=losowo wybrany obiecujacy potomek v;

}

return numnodes;

}

Dla algorytmu problemu n-królowych może to wyglądać.

________________________________________________________
Oszacowanie metodą Monte Carlo dla algorytmu z powrotami –
problem n
-królowych

Problem:
oszacowanie efektywności algorytmu

Dane wejściowe: dodatnia wartość całkowita n

Wynik: szacunkowa liczba węzłów w przyciętym drzewie przestrzeni
stanów, generowanym przez algorytm – liczba węzłów, jakie muszą
zostać sprawdzone przez algorytm przed wyszukaniem wszystkich
sposobów na ustawienie n królowych na szachownicy n

×

n tak, aby

się wzajemnie nie szachowały.

background image


int estimate_n_queens (int n)
{

index i,j,col[1..n];

int m,mprod,numnodes;

set_of_index prom_children;

i=0;

numnodes=1;

m=1;

mprod=1;

while (m!=0 && i!=n) {

mprod=mprod*m;

numnodes=numnodes+mprod*n;//Liczba wezłów t
i++; // wynosi n

m=0;
prom_children=∅; //Inicjalizacja zbioru

for(j=1;j<=n;j++){ //obiecujacych potomkow

col[i]=j; //pustym zbiorem

if(promising(i)){ //Okreslenie obiecuj.

m++; //potomkow.
prom_children=prom_children ∪ {j};

}

}
if (m!=0){

j= losowy wybór z prom_children;

col[i]=j;

}

}

return numnodes;

}

Algorytm Monte Carlo można uruchomić wielokrotnie i jako
właściwą wartość wykorzystać średnią z otrzymanych wyników.
Trzeba zauwazyć, że choć prawdopobieństwo uzyskania dobrego
oszacowania jest wysokie przy wielokrotnym uruchomieniu to nigdy
nie mamy gwarancji, że jest to dobre oszacowanie.

background image

Oszacowanie uzyskiwane dla dowolnego przypadku zastosowania
metody Monte Carlo jest prawdziwe tylko dla tego pojedynczego
przypadku. Zdarza się, że gdy mamy dwa różne przypadki dla takiej
samej wartości n, jeden może wymagać sprawdzenia niewielkiej
liczby węzłów, natomiast drugi przejrzenia całego drzewa przestrzeni
stanów.


Wyszukiwarka

Podobne podstrony:
AiSD Wyklad4 dzienne id 53497 Nieznany (2)
AiSD Wyklad9 dzienne id 53501 Nieznany
AiSD Wyklad6 dzienne id 53499 Nieznany (2)
AiSD Wyklad7 dzienne id 53500 Nieznany (2)
AiSD Wyklad3 dzienne id 53496 Nieznany (2)
AiSD Wyklad5 dzienne id 53498 Nieznany
AiSD Wyklad4 dzienne id 53497 Nieznany (2)
3 Wyklad OiSE id 33284 Nieznany
PIF2 2007 Wykl 09 Dzienne id 35 Nieznany
or wyklad 4b id 339029 Nieznany
Materialy do wykladu nr 5 id 28 Nieznany
Finanse Wyklady FiR id 172193 Nieznany
Folie wyklad2 Krakow id 286699 Nieznany
OP wyklad nr 3 id 335762 Nieznany
prc wyklad zagad 5 id 388963 Nieznany
AiSD Wyklad2 dzienne
AiSD Wyklad1 dzienne

więcej podobnych podstron