Witam
Czy ktos moglby opisac mi algorytm scalania w miejscu dwoch posortowanych
tablic, uzywajac jedynie stalej liczby komorek pamieci w czasie liniowym.
Ewentualnie jakis link do strony z opisanym algorytmem.
Z gory dziekuje.
i_a:=0;
i_b:=0;
for (i=0;i<(A0+B0);i++) {
if (i_a<A0) {
if (i_b<B0) {
if (A[i_a]<=B[i_b]) {
C[i]=A[i_a];
i_a++;
} else
{
C[i]=B[i_b];
i_b++;
}
} else
{
C[i]=A[i_a];
i_a++;
}
} else
{
if (i_b<B0) {
C[i]=B[i_b];
i_b++;
}
}
}
0) tablica A ma A0 rekordow, tablica B ma B0 rekordow
1) alokujesz nowa tablice C o liczbie rekordow A0+B0
merge(int A[1..k], int B[1..n])
{
int c[50]; // cos takiego moge zrobic
int *c = malloc((k+n) * sizeof(int)); // czegos takiego mi nie wolno
...
...
}
gdzie chcialbys przechowac wynik ?
No chyba ze w tych dwoch tablicach wejsciowych,
tylko musisz sobie wybrac ktora bedzie pierwsza, a ktora druga.
merge(int *T, int k, int n)
{
int c[50]; // ok
int *c = malloc( n * sizeof(int)); // nie moge tak :(
...
// analogicznie
z tym ze A-T[1]
B-T[k+1]
C-T[1]
A0=k
B0=n-k
// pobaw sie wskaznikami ;-)
// ... sortujesz w miejscu
i_a:=0;
i_b:=0;
for (i=0;i<(A0+B0);i++) {
if (i_a<A0) {
if (i_b<B0) {
if (A[i_a]<=B[i_b]) {
C[i]=A[i_a];
i_a++;
} else
{
C[i]=B[i_b];
i_b++;
}
} else
{
C[i]=A[i_a];
i_a++;
}
} else
{
if (i_b<B0) {
C[i]=B[i_b];
i_b++;
}
}
}
Bardzo fajny niedzialajacy program :)
Proponuje scalic np. taka tablice: T[2, 2, 2, 2, 1, 1, 1, 1] dla k=4.
To zadanie jest troche bardziej skomplikowane i przyznam sie ze nie wiem
jak to zrobic w czasie liniowym na tej samej tablicy.
pozdrawiam Robert
z tym ze A-T[1]
B-T[k+1]
C-T[1]
A0=k
B0=n-k
// pobaw sie wskaznikami ;-)
// ... sortujesz w miejscu
i_a:=0;
i_b:=0;
for (i=0;i<(A0+B0);i++) {
if (i_a<A0) {
if (i_b<B0) {
if (A[i_a]<=B[i_b]) {
C[i]=A[i_a];
i_a++;
} else
{
C[i]=B[i_b];
i_b++;
}
} else
{
C[i]=A[i_a];
i_a++;
}
} else
{
if (i_b<B0) {
C[i]=B[i_b];
i_b++;
}
}
}
Michal Poziemski pozwoliła sobie popełnić co następuje:
Pozdrawiam
Pozdrawiam
Piotr Wyderski
Piotr Wyderski pozwoliła sobie popełnić co następuje:
Pozdrawiam
PS: Oczywiście mogę się mylić.
I nikt nie twierdzi, że prawidłowy ;-
Pozdrawiam
Piotr Wyderski
Ale dzisiaj podam rozwiazanie, juz prawie wiem jak to zrobic ;-)
zgadza sie, "zadepcze" swoje dane.
Ale dzisiaj podam rozwiazanie, juz prawie wiem jak to zrobic ;-)
OK juz wymyslilem ;-)
Dane wejsciowe
Tablica T[1..n]
gdzie:
podtablica A[1..k]-T[1..k]
podtablica B[1..(n-k)]-T[k+1..n]
dlugosc(T)=T0=n
dlugosc(A)=A0=k
dlugosc(B)=B0=n-k
// Sortujemy A+B-T
// piszemy sobie 2 funkcje, ktore ulatwia nam manipulowanie tymi tabelami
// sorry... bedzie w pascalu ;-)
// przyjmuje ze tabele sa indeksowane od 1 (nie od 0) !!!
procedure sortuj(var A,B:array of integer);
var
i,i_lo,i_hi:integer;
buf:integer;
pom:integer;
procedure set(pozycja,wartosc);
begin
if pozycja<=high(A) then // w tym wypadku high() zwraca
dlugosc tablicy
A[pozycja]:=wartosc else
B[pozycja-high(A)]:=wartosc;
end;
function get(pozycja):integer;
begin
if pozycja<=high(A) then
result:=A[pozycja] else
result:=B[pozycja-high(A)];
end;
begin // glowna petla sortujaca
// inicjujemy wskazniki na pozycje stosu
i_lo:=2; poczatek tablicy A po wyjeciu pierwszego elementu
i_hi:=high(A)+1; poczatek tablicy B
// na poczatek "wyjmujemy" pierwszy element, zobaczycie po co w dalszej
czesci ;-)
buf:=get(1);
// iterujemy po wszystkich elementach
tablicy T(1..n)
for i:1 to (high(A)+high(B)) do
begin
// w kazdym obiegu dbamy o to aby "w reku" trzymac maksymalny
// element z 3-ech dostepnych: buf, T[i_lo], T[i_hi]
if (i_lo<=high(A)) then // zabezpieczamy sie aby nie "wejsc" na
tablice B
if buf<get(i_lo) then
begin
pom:=buf; // zamieniamy miejscami
buf:=get(i_lo);
set(i_lo,pom);
end;
if (i_hi<=(high(A)+high(B))) then // uwaga! nie wolno wyjsc poza
tablice
// GPF od reki ;-)
if buf<get(i_hi) then
begin
pom:=buf; // zamieniamy miejscami
buf:=get(i_hi);
set(i_hi,pom);
end;
// teraz skoro juz wiemy ze elementy T[i_lo],T[i_hi] sa
// mniejsze od buf
// przypadek 1: nie oproznilismy w calosci ktorejs z tabel A lub B
if (i_lo<=high(A)) and (i_hi<=(high(A)+high(B))) then
begin
if (get(i_lo)<=get(i_hi)) then
begin
set(i,get(i_lo)); // zdejmujemy z listy T[i_lo]
inc(i_lo);
end else
begin
set(i,get(i_hi)); // zdejmujemy z listy T[i_hi]
inc(i_hi);
end;
// buf zostaje bez zmian
end else
// przypadek 2: tabela B zostala wyprozniona w calosci
if (i_lo<=high(A)) and (i_hi(high(A)+high(B))) then
begin
set(i,get(i_lo)); // przenosimy T[i_lo]-T[i]
inc(i_lo);
// buf bez zmian, bo jest wiekszy ;-)
end else
// przypadek 3: tabela A zostala wyprozniona w calosci
if (i_lohigh(A)) and (i_hi<=(high(A)+high(B))) then
begin
set(i,get(i_hi));
inc(i_hi);
// buf bez zmian bo jest wiekszy
end else
// przypadek 4: obie tabele zostaly wyproznione, a w
"lapie" mamy element maksymalny
begin
set(i,buf); // wkladamy go na koniec tabeli T[n]
end;
end;
end;
// Voila! I nawet dziala ;-)
Sprawdz jeszcze raz ten algorytm. Mam dziwne wrazenie ze znowu
podales
rozwiazenie, ktore nie dziala.
pzdrv Robert
Czas: O(n)
P.S.
To ze nie potrafisz wymyslic jakiegos algorytmu to
wcale nie znaczy ze on nie istnieje ;-)
Kurde to ja jestem "niewierny" Tomasz, wiec nie rozumiem
dlaczego mi wkladasz paluchy w rany ;-))))))))
P.S.
To ze nie potrafisz wymyslic jakiegos algorytmu to
wcale nie znaczy ze on nie istnieje ;-)
a) wyciagamy pierwszy element, aby miec wolne miejsce,
jezeli tego nie zrobimy to musielibysmy przegladac
kazda tablice w gore, aby sie upewnic ze jest nadal posortowana
---- a czas mial byc liniowy ;-)
b) staramy sie nie zaburzyc posortowania tablic, dlatego
dazymy do tego aby trzymac maksymalny element z 3-ech
w "reku"
c) podaj przyklad ktory obali jego dzialanie ;-)
Moj dziala, a algorytmu Knutha nie widzialem 8-(
Jak ktos zna ten drugi to ew. moze porownac,
ale obawiam sie ze bardziej krotkie i zwarte rozwiazanie nie istnieje.
To co wymyslilem wynika z logiki:
a) wyciagamy pierwszy element, aby miec wolne miejsce,
jezeli tego nie zrobimy to musielibysmy przegladac
kazda tablice w gore, aby sie upewnic ze jest nadal posortowana
---- a czas mial byc liniowy ;-)
b) staramy sie nie zaburzyc posortowania tablic, dlatego
dazymy do tego aby trzymac maksymalny element z 3-ech
w "reku"
c) podaj przyklad ktory obali jego dzialanie ;-)
Dobra, zacznijmy.
Nie mam Pascala , bo go nie lubie, ale jakos damy sobie rade:
tablica T[22341111] dla k =4
po pierwszej iteracji T wyglada tak:
[12341111] i_lo=2 i_hi=6 i=1 (jezeli liczymy indeksy tablicy od 1)
zmienna buf=2
druga iteracja:
[11241111] ,i_lo=2 ,i_hi=7, buf =3, i=2 (juz sie zaczyna....)
trzecia iteracja:
[11131111] i_lo=2, i_hi=8, buf=4 ,i=3 (ooo.... gdzies znikla 2)
chyba nie trzeba dalej...
- koniec obalenia twojego wywodu -
zwracam honor .... jest blad ;-))))))
Dzieki za ten egzample.... algorymt sie zadlawil az mu uszmai poszlo.
Potem pomysle jak go skorygowac..
Trzeba dac mozliwosc "przesiedlania" tabel, a dokladniej
zamiast traktowac je liniowo tak jak zrobilem, powinienem je potraktowac
jak bufory okrezne.
Ten twoj przypadek jest swoisty w kazdym calu ;-)
A mianowicie cala podtabela A powinna sie znalezc za tabela B....
Po poludniu podam rozwiaznie poprawione.
Jest tylko jedno ale. Nie dalbym gwarancji ze ten algorytm ma liniowa
zlozonosc. Wydaje mi
sie tak, ale nie jestem tego na 100% pewien.
w kazdym badz razie powodzenia
pozdrawiam Robert
Juz wiem o co chodzi ;-)
Trzeba dac mozliwosc "przesiedlania" tabel, a dokladniej
zamiast traktowac je liniowo tak jak zrobilem, powinienem je potraktowac
jak bufory okrezne.
Ten twoj przypadek jest swoisty w kazdym calu ;-)
A mianowicie cala podtabela A powinna sie znalezc za tabela B....
Po poludniu podam rozwiaznie poprawione.
[112345678]
^ ^
end start wtedy 567811
Jest tylko jedno ale. Nie dalbym gwarancji ze ten algorytm ma liniowa
zlozonosc. Wydaje mi
sie tak, ale nie jestem tego na 100% pewien.
ten pomysl z buforowaniem "robakow" w miejscu jest znacznie lepszy ...
| Bardzo fajny niedzialajacy program :)
| Proponuje scalic np. taka tablice: T[2, 2, 2, 2, 1, 1, 1, 1] dla k=4.
| To zadanie jest troche bardziej skomplikowane i przyznam sie ze nie
wiem
| jak to zrobic w czasie liniowym na tej samej tablicy.
| zgadza sie, "zadepcze" swoje dane.
| Ale dzisiaj podam rozwiazanie, juz prawie wiem jak to zrobic ;-)
trzymam kciuki
pzdrv Robert
przeszkadza gorace powietrze
Roznice pasma 2,4GHz, a 5 GHz
Czym spakować ADF
jaki Webcam do maca...
Usuniecie danych z dysku RAID1
! Programista czy koder?
his i amiga?