Kolory i kompresja

20.04.2010 - Krzysztof Dryś
TrudnośćTrudność

Czy uważaliście na biologii?

Człowiek tak na prawdę widzi tylko trzy kolory: czerwony, zielony i niebieski. Właśnie dlatego obrazek zapisujemy jako trzy macierze R,G i B - jest to sposób dla nas najbardziej naturalny. Jak sami się przed chwilą przekonaliśmy, spośród tych trzech kolorów najlepiej rozróżniamy zielony. Wytłumaczyć to można (nie do końca na poważnie) tym, że ludzie pierwotni większą część swojego czas spędzali w lasach. I dlatego musieli dobrze rozpoznawać rośliny oraz kryjące się między nimi zwierzęta.

Jeżeli uważaliście na biologii to wiecie, że w ludzkim oku znajdują się pręciki i czopki. Pierwsze odpowiadają za za widzenie czarno-białe, drugie za widzenie barwne. Pręcików jest dużo więcej i są dużo czulsze. To między innymi dlatego, gdy jest ciemno, nie widzimy kolorów.

No dobrze, ale co to właściwie ma wspólnego z kompresją obrazków? Możemy wykorzystać to, że lepiej rozpoznajemy jasność obiektów niż ich kolor. W tym celu wprowadzimy nową reprezentację obrazków. Do tej pory trzy macierze R,G i B mówiły ile jest poszczególnych kolorów w pikselach. Teraz, zamiast tego, będzie posługiwali się macierzami $ Y $, $ Cr $ i $ Cb $.

Jasność piksela

W tym wypadku trudniej będzie o łatwą i ładną interpretację tego, co te macierze zawierają. Pierwsza z nich, macierz $ Y $, mówi o jasności piksela. Czyli o tym, jak jasny wyda się nam piksel o określonych kolorach. Ta wartość wyraża się wzorem:

$$ Y[i,j] = 0.299 \cdot R[i,j] + 0.587 \cdot G[i,j] + 0.114 \cdot B[i,j]$$
Należy podkreślić, że ten wzór jest eksperymentalny i przybliżony. To znaczy, że nie da się go teoretycznie wyprowadzić. Powstał na skutek przeprowadzenia wielu doświadczeń.

Czy ten wzór jest ciekawy? Zdecydowanie! Przede wszystkim, jest kolejnym potwierdzeniem faktu, który my już przed chwilą zauważyliśmy: nie ma równości między kolorami. Zauważmy bowiem, że współczynniki przy czerwonym, zielonym i niebieskim są różne. Oznacza to, że zielony piksel wydaje się nam jaśniejszy od niebieskiego piksela. Najlepiej zobaczyć to na przykładzie:

alternative text Powyżej widzimy trzy (czyste) kolory. Najjaśniejszy wydaje się zielony, a najciemniejszy niebieski.

Macierz $ Y $ zawiera informacje o jasności. Potrzeba nam więc jeszcze informacji o kolorze. Jest ona zawarta w macierzach $ Cb $ i $ Cr $. Właśnie dlatego nazywa się je komponentami chromatycznymi. Definiuje się je w następujący sposób:

To nie są dokładne wzory! Ale dokładne wzory nie są zbyt ciekawe. A my chyba mamy już na dzisiaj dosyć cyferek, prawda? Gdyby ktoś jednak chciał dokładniej poznać podział na składowe YCrCb, to może skorzystać z artykułu na Wikipedii.

$ Cr[i,j] \approx R[i,j] - Y[i,j] $

$ Cb[i,j] \approx B[i,j] - Y[i,j] $

No dobrze, ale po co nam tak właściwie te macierze? I jaki ma to związek z kompresją? Jesteśmy już coraz bliżej odpowiedzi na to pytanie. Najpierw popatrzmy na rozkład naszego obrazka na składowe Y,Cr i Cb:

alternative text alternative text alternative text Od lewej: składowa Y, składowa Cr i składowa Cb naszego obrazka.

Gdy rozkładaliśmy obrazek na składowe R,G i B to wszystkie kanały były (do pewnego stopnia) czarno-białą wersją oryginału. Tym razem już tak nie jest. Tylko składowa $ Y $ przypomina oryginał. Nie da się tego powiedzieć o pozostałych. Kanały $ Cr $ i $ Cb $ gubią wiele szczegółów. Nie zobaczymy na nich śniegu, faktury dachu, a trawa jest ledwie rozpoznawalna. W pewnym sensie składowa $ Y $ niesie dużo więcej informacji niż składowe $ Cr $ i $ Cb $.

Dla nas jest to świetna wiadomość. Oznacza ona, że możemy pozwolić sobie na stratną kompresję składowych chromatycznych, bo i tak niewiele one wnoszą do naszego obrazka.

Sprytniejszy algorytm kompresji

Popatrzmy na poniższy algorytm:

1
2
3
4
5
6
(R,G,B) - kolorowy obrazek do skompresowania.
y,cr,cb - parametr określający stopień kompresji poszczególnych kanałów.
Przekształć obrazek do postaci (Y,Cr,Cb)
Dla warstwy Y zapisz średnie kwadratów o boku y,
Dla warstwy Cr zapisz średnie kwadratów o boku cr,
Dla warstwy Cb zapisz średnie kwadratów o boku cb,
Oraz na odpowiadający mu algorytm dekompresji:
1
2
3
Wczytaj średnie dla kanałów Y,Cr i Cb
Na podstawie średnich odtwórz kanały Y,Cr i Cb
Przekształć obrazek do postaci (R,G,B)
Jako, że składowa Y jest ważniejsza od składowych $ Cr $ i $ Cb $, to zazwyczaj będziemy stosowali nasz algorytm z parametrem $ y $ mniejszym od parametrów $ cr $ i $ cb $.

Cała ta teoria brzmi mądrze. Ale najlepiej od razu sprawdzić, jak nasz algorytm zachowuje się w praktyce. W tym celu uruchomimy go dla różnych zestawów parametrów (y,cr,cb).

alternative text Wynik działania algorytmu z parametrami (y=4,cr=1,cb=1). To znaczy: dla warstwy jasności pamiętamy jedynie średnie kwadratów o boku 4. Dla warstw chromatycznych pamiętamy wszystkie piksele.
alternative text Wynik działania algorytmu z parametrami (y=16,cr=1,cb=1). To znaczy: dla warstwy jasności pamiętamy jedynie średnie kwadratów o boku 4. Dla warstw chromatycznych pamiętamy wszystkie piksele.
alternative text Wynik działania algorytmu z parametrami (y=1,cr=4,cb=4). To znaczy: dla warstw chromatycznych pamiętamy jedynie średnie kwadratów o boku 4. Dla warstwy jasności pamiętamy wszystkie piksele.
alternative text Wynik działania algorytmu z parametrami (y=1,cr=16,cb=16). To znaczy: dla warstw chromatycznych pamiętamy jedynie średnie kwadratów o boku 16. Dla warstwy jasności pamiętamy wszystkie piksele.

Te obrazki są dowodem na to, że składowa Y jest dużo ważniejsza od składowych Cr i Cb. Przy zastosowaniu parametrów $ (y = 1, cr = 4, cr = 4) $ prawie nie widać różnicy względem orginalnego obrazka. Przy zestawie $ (y = 1, cr = 16, cr = 16) $ widać trochę przebarwień, szczególnie na krawędziach. Ale ogólne wrażenie jest raczej pozytywne. Natomiast przy zestawie $ (y = 4, cr = 1, cb = 1) $ obrazek staje się zamazany i niewyraźny. Wreszcie zestaw $ (y = 16,cr = 1, cb = 1) $ powoduje, że na obrazku ciężko coś zobaczyć.

5
Twoja ocena: Brak Ocena: 5 (1 ocena)

Copyright © 2008-2010 Wrocławski Portal Informatyczny

design: rafalpolito.com