2011-08-09 17 views
12

Mam katalog zdjęć, zdjęć, grafiki internetowej, logo, itp ... wszystkie są wyciągane z internetu. Dostępne są pliki .jpg, .gif i .png.Jak odróżnić grafikę od fotografii?

Chciałbym wyodrębnić obrazy, które są prawdziwe (zachowaj zdjęcia i usuń grafikę). Nie próbuję uzyskać prawdziwych/oryginalnych zdjęć, tylko obrazów z prawdziwego życia w porównaniu z grafiką komputerową (nie jestem pewien, jak to powiedzieć bardziej wyraźnie). Prawie wszystkie z tych zdjęć zostały zmanipulowane, a informacje o nich nie będą dostępne.

Duży (nawet bardzo duży) margines błędu jest akceptowalny.

mam już:

  • usunąć obrazy z małą liczbą kolorów przy użyciu imagecolorstotal()
  • usuniętych obrazów, które mają duże wysokości do szerokości wskaźników i odwrotnie (stosunek 3+ działa zaskakująco dobrze).
  • usunąć obrazy, które są mniejsze niż pewien wymiar (50-75px jest dobry)

myślę o usunięciu obrazów o wartości histogramów skupionych wokół pewnych kolorów, zamiast gładkiego lub rozproszonego krzywej. Nie próbowałem tego jeszcze.

Jak inaczej mogę poprawić to filtrowanie obrazów, aby wyodrębnić (głównie) prawdziwe zdjęcia? Wolę używać PHP, ale nie jest to wymagane.

AKTUALIZACJA: Okazuje się, że dla mojej aplikacji pierwsze trzy rzeczy, które wypróbowałem, to solidne 80% rozwiązanie. Dalsze filtrowanie można wykonać za pomocą niektórych odpowiedzi poniżej.

+0

Można użyć biblioteki GD, aby móc przetwarzać surowe dane obrazu i sprawdzić takie rzeczy jak krawędzie, Obraz podobieństwa i inne rzeczy. Chciałbym opublikować coś bardziej precyzyjnego, ale php.net wydaje się być w tym momencie niedostępny. Użyłem GD wcześniej, aby wstawić znaki wodne i tym podobne, jest to trochę skomplikowane, ale można też z nim wiele zrobić. –

+0

co powiesz na sprawdzenie 'exif'? - http://php.net/manual/en/book.exif.php – ajreal

Odpowiedz

2

Poniżej znajduje się kod, którego użyłem i uzasadnienie, dlaczego zastosowałem każdy filtr. Zrobiłem wiele testów na tych funkcjach i ustawieniach, ale nadal będziesz chciał przeprowadzić kilka testów, aby zoptymalizować te ustawienia dla swojego zestawu obrazów.

Użyłem IMagick (obwoluta PHP dla ImageMagick) do pracy przy obliczaniu następujący obraz atrybuty:

$Image  = new Imagick($image_path); 
$height  = $Image->getImageHeight(); 
$width  = $Image->getImageWidth(); 
$histogram = $Image->getImageHistogram();    
$num_colors = $image->getImageColors(); 

Stosunek wysokości do szerokości

filtrowania obrazów stosunek wysokości do szerokości eliminuje duży procent śmieci. Im bliżej ustawienia filtra na 1: 1, tym lepszy będzie ten filtr, ale zaczniesz także filtrować wiele dobrych zdjęć. Jest to jeden z najcenniejszych filtrów Mam stosowanych:

// max height to width ratio we allow on images before we junk them 
$max_size_ratio = 3; 
if($size_ratio > $max_size_ratio) 
    throw new Exception("image height to width ratio exceeded max of $max_size_ratio"); 

ilość kolorów

zdjęć filtracyjne poniżej 32 kolorach zazwyczaj tylko usuwa niepotrzebne obrazy, ale ja również utracone du? O czarno-białe diagramy i rysunki.

// min number of colors allowed before junking 
$min_colors = 32; 
if($num_colors < $min_colors) 
    throw new Exception("image had less than $min_colors colors"); 

Minimalna wysokość i szerokość

obrazy filtrowania na podstawie bezwzględnej minimalnej wysokości i szerokości, że zarówno wymiary muszą przechodzić, a także o nieco większej wartości, że co najmniej jeden wymiar musi przejść pomógł odfiltrować trochę śmieci.

// min height and width in pixels both dimensions must meet 
$min_height_single = 50; 
$min_width_single = 50; 
if(
    $width < $min_width_single 
    OR $height < $min_height_single 
) 
    throw new Exception("height or width were smaller than absolute minimum"); 

// min height and width in pixels at least one dimension must meet 
$min_height = 75; 
$min_width = 75; 
if(
    $width < $min_width 
    && $height < $min_height 
) 
    throw new Exception("height and width were both smaller than minimum combo"); 

Barwa Entropia Korzystanie z histogramu obrazu

Wreszcie obliczyć entropię kolorów obrazu (jak sugeruje @Jason w swojej odpowiedzi) dla każdego obrazu w moim systemie. Kiedy wybieram obrazy do wyświetlenia, generalnie uporządkuję je w rankingu według tej entropii w malejącej kolejności. Im wyższa entropia, tym bardziej prawdopodobne jest, że obraz będzie fotografią rzeczywistości, a nie grafiki. Istnieją trzy główne problemy związane z tą metodą:

  1. Wysoce stylizowane grafiki mają zwykle wyższe entropii powodu wielkiej zmienności głębokości kolorów i barw.

  2. Zdjęcia, które zostały poddane photoshopped w celu uzyskania jednolitego tła i tła studyjnego, mają zazwyczaj niższą entropię z powodu dominującego jednolitego koloru.

  3. To nie działało dobrze jako filtr absolutny ze względu na duże różnice między obrazami w moim zestawie, ich typami plików, głębi kolorów itd. Jednak w przypadku wybrania najlepszego zdjęcia z mały podzbiór w całym moim zestawie. Przykładem może być wybór obrazu wyświetlanego jako obraz główny ze wszystkich obrazów znalezionych na jednej stronie.

Oto funkcja użyć do obliczenia obrazu entropię:

function set_image_entropy() 
{ 

    // create Imagick object and get image data 
    $Image = new Imagick($this->path); 
    $histogram = $Image->getImageHistogram();    
    $height = $Image->getImageHeight(); 
    $width = $Image->getImageWidth(); 
    $num_pixels = $height * $width; 

    // calculate entropy for each color in the image 
    foreach($histogram as $color) 
    { 
     $color_count = $color->getColorCount(); 
     $color_percentage = $color_count/$num_pixels; 
     $entropies[] = $color_percentage * log($color_percentage, 2); 
    } 

    // calculate total image color entropy 
    $entropy = (-1) * array_sum($entropies); 

    return $entropy; 

} 
7

Funkcja exif_read_data może dostarczyć informacji o używanych kamerach, różni się znacznie w przypadku każdej kamery. To nie będzie idealne rozwiązanie, ale powinno dodać do tego, czego już używasz.

+0

to świetna propozycja, ale większość z tych zdjęć została zmanipulowana, a informacje exif nie są dostępne. są obrazami internetowymi, a nie oryginalnymi. –

1

Grafika i rysunek linii są zwykle mniejsze, gdy są zapisane jako png, a zdjęcia są mniejsze, gdy są zapisane jako jpg. Przechowuj każdy obraz w każdym formacie i zgadnij, ile wynosi rozmiar pliku.

6

Entropy byłby dobrym wskaźnikiem odróżniającym "prawdziwe" zdjęcia od grafiki komputerowej. Jest to po prostu bardziej ustrukturyzowana wersja twojego pomysłu na histogram. Entropia jest podana przez

gdzie p [i] jest prawdopodobieństwem i-tego koloru. p[i] to właściwie wartość histogramu dla każdego koloru (procent (0,0-> 1,0) pikseli koloru i). Im bardziej rozproszone są kolory, tym wyższa będzie wartość H(X). Jeśli piksele są rozmieszczone tylko w kilku kolorach, H(X) będzie małe.

Zwróć uwagę, że skompresowany rozmiar pliku jest bezpośrednio związany z entropią (wyższa entropia, większy rozmiar pliku), więc sugestia w innej odpowiedzi na użycie rozmiaru pliku może być pośrednim sposobem uzyskania tego.

+0

wszelkie sugestie, jak obliczyć p [i] z php? –

+1

p [i] jest po prostu histogramem obrazu, więc powinieneś być w stanie znaleźć jakiś kod php, aby to obliczyć. Tylko upewnij się, że histogram jest podany w procentach (0.0-> 1.0), a nie w surowych zliczeniach każdego koloru. Upewnij się również, że zdefiniowałeś specjalny przypadek log2 (0) = 0, który jest zazwyczaj niezdefiniowany. –

Powiązane problemy