Documente Academic
Documente Profesional
Documente Cultură
Metoda Greedy este una din cele mai directe tehnici de proiectare a
algoritmilor care se aplica la o varietate larga de probleme.In general,aceasta
metoda se aplica problemelor de optimizare.Specificul acestei metode consta
in faptul ca se construieste solutia optima pas cu pas,la fiecare pas fiind
selectat(sau „inghitit”) in solutie elementul care pare „cel mai bun”la
momentul respectiv,in speranta ca va duce la solutie optima globala.
In metoda Greedy soluţia problemei se caută prin testarea consecutivă a
elementelor din mulţimea A şi prin includerea unora din ele în submulţimea
B.
***Într-un limbaj plastic, submulţimea B încearcă să „înghită” elementele
„gustoase” din mulţimea A, de unde provine şi denumirea metodei .
!!!(greedy lacom, hrăpăreţ).
*Tehnica Greedy este una de optimizare, ruland mai rapid decat un
Backtraking.
*Complexitatea unui algoritm greedy este polinomiala.
Dezavantaje:
*Cand nu aveti o idee mai buna legata de o problema, in timpul unui concurs,
o implementare Greedy ar putea aduce doar in jur de 30% din punctaj.
*Exista situatii in care algoritmii clacheaza, cum ar fi problema comisului
voiajor.
* Cu regret, metoda Greedy poate fi aplicată numai atunci cînd din enunţul
problemei poate fi dedusă regula care asigură selecţia directă a elementelor
necesare din mulţimea A.
*Funcţia ExistaElemente returnează valoarea true dacă în mulţimea A există
elemente care satisfac criteriul (regula) de selecţie.
*Procedura AlegeUnElement extrage din mulţimea A un astfel de element x,
iar procedura IncludeElementul înscrie elementul selectat în submulţimea B.
!!! Iniţial B este o mulţime vidă.
În programul ce urmează mulţimile A şi B sînt reprezentate prin vectorii
(tablourile unidimensionale) A şi B, iar numărul de elemente ale fi ecărei
mulţimi prin variabilele întregi, respectiv n şi m. Iniţial B este o mulţime
vidă, respectiv m=0.
while ExistaElemente do
begin
AlegeUnElement(x);
IncludeElementul(x);
end
Structura:
Această metodă presupune că problemele pe care trebuie să le rezolvăm au
următoarea structură:
-se dă o mulţime A={a1, a2, ..., an} formată din n elemente;
- se cere să determinăm o submulţime B, care îndeplineşte anumite condiţii
pentru a fi acceptată ca soluţie.
Descriere
Metoda greedy se folosește pentru problemele în care, dându-se o mulțime
finită A, trebuie determinată o mulțime S⊂A care să îndeplinească anumite
condiții.
Metoda furnizează o singură soluție reprezentată prin elementele mulțimii S.
ca și în cazul metodei backtracking soluția problemei este dată de un vector
S = {x 1, x 2 ...xn} ale cărui elemente aparțin însă unei singure mulțimi A.
Spre deosebire de metoda backtracking metoda greedy nu găsește decât o
singură soluție și în general această soluție este soluția optima.
Ex.1. Spectacole
https://www.youtube.com/watch?v=U-h-mzr6_AU
Să se repartizeze optim o resursă (de ex. sala de spectacole, conferințe, sport
etc.) mai multor activități care concurează pentru resursa respectivă.
Mulțimea A este formată din cele n activități. Fiecare activitate i cu
(1≤ i≤ n) n are un timp de începere ti și un timp de terminare tf unde ti<fi și
ocupă resursa în intervalul de timp [ti, fi]. Două activități i și j sunt compatibile
dacă intervalele lor de ocupare [ti fi] și [tj fj] sunt disnjuncte, Adică dacă fi ≤ tj
sau dacă e fj ≤ ti. Cerința problemei este de a selecta o mulțime maximală de
activități compatibile. In acest caz mulțimea S este formată din activitățile care
vor folosi resursa, iar condiția pe care trebuie să o îndeplinească elementele
mulțimii s este ca ele să fie activități compatibile. In plus pentru ca repartizarea
resursei să fie optimă trebuie ca mulțimea S să conțină maximul de elemente
care îndeplinesc această condiție.
Ex.2 Să se ocupe optim un mijloc de transport(de ex. un rucsac, un camion,
etc.) care are o capacitate maximă de ocupare(poate transporta o greutate
maximă G) cu n obiecte, fiecare obiect având greutatea gi și un profit obținut
în urma transportului ci, iar din fiecare obiect putând să se ia o fracțiune xi
[0,1]
Mulțimea A este formată din cele n obiecte. Fiecare obiect i (1 ≤i≤n)are
eficiență a transportului ei care reprezintă profitul pentru o unitate de
greutate. Cerința problemei este de a selecta o mulțime de obiecte astfel
încât eficiență a transportului să fie maximă. Mulțimea S este formată din
obiectele care vor ocupa mijlocul de transport iar condiția pe care trebuie să
o îndeplinească elementele mulțimii S este ca prin contribuția adusă de
fiecare obiect la eficiența transportului să se obțină o eficiență maximă iar
greutatea obiectelor selectate să fie egală cu greutatea maximă a
transportului
Ex.3 Pentru două mulțimi de numere întregi nenule C cu n elemente
C={c1,c2,…cn}și A cu m elemente A={a1,a2,…am} și n ≤m, Să se selecteze o
submulțime de n elemente din mulțimea A astfel încât expresia
E=c1*x1+c2*x2+…..+cn*xn
în care xi ∈ A să aibă valoarea maximă.
Managerul artistic al unui festival trebuie sa selecteze o multime cat mai ampla
de spectacole ce pot fi jucate in singura sala pe care o are la dispozitie.Stiind ca i
s-au propus n spectacole si pentru fiecare spectacol i-a fost anuntat intervalul in
care se poate desfasura [Si, Fi] (Si reprezinta ora si minutul de inceput, iar Fi ora
si minutul de final al spectacolului i), scrieti un program care sa permita
spectatorilor vizionarea unui numar cat mai mare de spectacole.
Date de intrare
Pe prima linie a fisierului de intrare spectacole.in se afla numarul n, numarul de
spectacole propus. Pe urmatoarele n linii se vor afla 4 valori, primele doua
reprezentand ora si minutul inceperii spectacolului curent, iar ultimele doua
reprezentand ora si minutul terminarii spectacolului.
Date de iesire
Fisierul de iesire spectacole.out contine o singura linie, pe aceasta vor fi scrise
numerele de ordine ale spectacolelor care indeplinesc solutia problemei, printr-un
spatiu.
Restrictii n <= 100
spectacole.in spectacole.out
Descrierea solutiei
Vom sorta crescator spectacolele dupa ora
de final. Vom selecta initial primul spectacol
5 (cel care se termina cel mai devreme). In
12 30 16 30 continuare vom selecta, la fiecare pasa,
15 0 18 0 primul spectacol neselectat, care nu se
524 suprapune peste cele deja selectate.
10 0 18 30
18 0 20 45
O implementare intuitiva a acestui algoritm
12 15 13 0
va fi prezentata in continuare. Pentru sortat
vom folosi metoda BubbleSort, care este
indeajuns de buna pentru limitele impuse de
problema.
void sorteaza()
#include <iostream>
#include <fstream> {
using namespace std; int aux,schimb,i;
do
ifstream f("spectacole.in"); {
ofstream g("spectacole.out"); schimb=0;
int n,inceput[100],sfarsit[100],nr[100]; for (i=0;i<n-1;++i)
if
void citeste() (sfarsit[nr[i]]>sfarsit[nr[i+1]])
{
{
int ora,min,i;
f>>n; aux=nr[i];
for (i=0;i<n;++i) nr[i]=nr[i+1];
{ nr[i+1]=aux;
nr[i]=i+1; schimb=1;
f>>ora>>min; }
inceput[i]=ora*60+min; }
f>>ora>>min; while (schimb);
sfarsit[i]=ora*60+min; }
}
f.close();
}
void rezolva()
{
int ultim,i;
for (ultim=0,i=1;i<n;++i)
if (inceput[nr[i]]>=sfarsit[nr[ultim]])
{
g<<nr[i]+1<<" ";
ultim=i;
}
g<<endl;
}
int main()
{
citeste();
sorteaza();
rezolva();
return 0;
}
Problema fractionara a rucsacului
void afisare()
{
int i; https://www.youtube.com/watch?v=xLsuudvmrtg
for (i=0;i<N;++i)
if (x[i]) g<<i+1<<" problema #1340 Rucsac - pbinfo.ro
"<<x[i]*100<<endl;
g.close();
}
Colorarea hartii folosind metoda Greedy.
Fiind data o harta cu n tari, se cere o solutie de colorare a hartii, utilizand cel mult patru culori,
astfel incat doua tari ce au frontiera comuna sa fie colorate diferit. Este demonstrat faptul ca
sunt suficiente numai patru culori pentru ca orice harta sa poata fi colorata.
colorare.in colorare.out
6 1 alb
alb verde galben rosu 2 verde
12 3 galben
13 4 verde
14 5 rosu
15 6 galben
16
23
25
26
34
35
45
56
#include <fstream>
using namespace std;
ifstream fin("colorare.in");
ofstream fout("colorare.out");
int A[101][101];// A[i][j]==1 pt tari vecine, 0 altfel
int X[101],n;//X[i]=indicele culorii tarii i
char C[5][21];//culorile
void afisare()
{
for(int i=1;i<=n;i++)
fout<<i<<" "<<C[X[i]]<<"\n";//afisez tara si culoarea
fout<<endl;
}
int valid(int k)
{//1 daca tara k poate fi colorata cu X[k], 0 altfel
for(int i=1;i<k;i++)//pt tarile colorate deja
if(A[i][k]==1 && X[i]==X[k]) return 0;//exita tara invecinata care are aceeasi culoare=>0
return 1;
}
int alege(int k)
{//alege culoarea minima valida
for(int i=1;i<=4;i++)//am 4 culori
{
X[k]=i;//plasez culoarea
if(valid(k)) return i;//daca e buna o returnez
}
return 0;//daca nu putem colora
}
void colorare()
{//plaseaza in X[i] culoarea tarii i
for(int i=1;i<=n;i++)
X[i]=alege(i);//culoarea minima
}
int main()
{
int t1,t2;
fin>>n;//citesc nr de tari
for(int i=1;i<=4;i++)
fin>>C[i];//citesc culorile
while(fin>>t1>>t2)//pereche de tari vecine
{
A[t1][t2]=1;//pun 1 in matrice
A[t2][t1]=1;
}
colorare();
afisare();
return 0;
}
Plata unei sume de bani cu bancnote date
Se citesc 3 numere naturale S, n si e cu urmatoarele semnificatii: S este o suma de
bani care trebuie platita folosind bancnote care au valori puterile lui e de la 1 la e la
n. Se se afiseze modalitatea de plata folosind un numar minim de bancnote de tipurile
precizate. Sa se afiseze la final numarul de bancnote folosite. Datele se vor citi din
fisierul eur.in, iar rezultatele se vor afisa in fisierul eur.out.
eur.in eur.out
#include <iostream>
using namespace std;
int s[10],a[10][10],n,i,j,v,p,vs,vs1,mint,cost;
int main()
{
cout<<"Numar noduri=";cin>>n;
for(i=1;i<=n;i++)
for(j=i+1;j<=n;j++)
cout<<"A["<<i<<"]["<<j<<"]=",cin>>a[i][j],a[j][i]=a[i][j];
cout<<"Nod de pornire:";cin>>v; s[v]=1;
vs1=v;
cout<<"Drumul trece prin:"<<v<<' ';
p=v;
for(i=1;i<n;i++)
{
mint=3000;
for(j=1;j<=n;j++)
if(a[v][j]!=0&&s[j]==0&&mint>a[v][j])
{
mint=a[v][j];
vs=j;
}
cost+=a[v][vs];
cout<<vs<<' ';
s[vs]=1;
v=vs;
}
cout<<p;
cost+=a[vs1][v];
cout<<endl<<"Cost="<<cost;
}