Hallo nochmal! Ich habe diesen Artikel gefunden, der bereits im Mai 2019 geschrieben wurde. Dies ist eine Fortsetzung einer Artikelreihe über WAVE und JPEG. Diese Veröffentlichung wird Informationen über den Bildcodierungsalgorithmus und das Format selbst enthalten.
Ein Hauch von Geschichte
Ein Esslöffel Wikipedia-Artikel:
JPEG (Joint Photographic Experts Group) ist eines der gängigsten Rastergrafikformate, das zur Speicherung von Fotobildern und ähnlichen Bildern verwendet wird.
Dieser Standard wurde 1991 von der Joint Photographic Experts Group für eine effektive Bildkompression entwickelt.
Welchen Weg Bilder von ihrer Rohform zum JPEG nehmen
Manche glauben, JPEG-Bilder sind komprimierte Rohdaten, die mit Huffman kodiert sind, aber das ist nicht korrekt. Bevor die endgültige Kompression erfolgt, durchlaufen die Daten einen langen Prozess.
Zuerst wird das Farbmodell von RGB auf YCbCr geändert. Dafür gibt es sogar einen speziellen Algorithmus — Y bleibt unverändert, da es für die Helligkeit verantwortlich ist, und jede Änderung wird auffällig sein.
Das Erste, was mit dem Bild gemacht wird, ist das 'Sondern' oder 'Pruning' (subsampling). Es ist ganz einfach: Ein 2x2 Pixelsatz wird genommen, anschließend werden Cb und Cr — die Durchschnittswerte jeder der YCbCr-Komponenten dieser 4 Pixel — ermittelt. Und so, haben wir 6 Byte gespart, anstatt 4 Y, 4 Cb, 4 Cr haben wir 4 Y und identische Cb und Cr für alle (4 + 4 + 4 = 12; 4 + 1 + 1 = 6; 12 - 6 = 6). Selbst bei einem 2×2 raster klingt eine Verlustkompression mit einem Kompressionsfaktor von 2:1 solid. Dies wird auf das gesamte Bild angewendet. So haben wir die Größe halbiert. Und diese Technik können wir aufgrund unserer Farbwahrnehmung nutzen. Ein Mensch wird den Unterschied in der Helligkeit leicht bemerken, jedoch nicht in der Farbe, wenn sie in einem kleinen Pixelsatz gemittelt wird. Auch kann das Subsampling zeilenweise durchgeführt werden, 4 Pixel horizontal und vertikal. Die erste Variante wird häufiger verwendet. Wenn die Bildqualität wichtig ist, wird das Subsampling überhaupt nicht durchgeführt.
Eine anschauliche Illustration des Subsamplings (Habr erlaubte nicht, das GIF einzufügen) —
Der Hauptteil der Vorbereitung
DCT
Jetzt kommt der schwierigste und notwendigste Teil. Das gesamte Bild wird in 8×8 Blöcke unterteilt (es wird Padding verwendet, falls die Auflösung nicht ein Vielfaches der Blockseite ist).
Jetzt wird auf jeden Block angewendet DCT (Diskrete Kosinus-Transformation). In diesem Teil werden aus dem Bild alle überflüssigen Teile entfernt. Mit DCT muss festgestellt werden, ob dieser Block (8×8) einen monotonen Teil des Bildes beschreibt, wie den Himmel oder eine Wand, oder ob er eine komplexe Struktur enthält (Haare, Symbole usw.). Es ist logisch, dass 64 ähnliche Pixel in Farbe nur durch 1 beschrieben werden können, da die Blockgröße bereits bekannt ist. Hier haben wir die Kompression: 64 zu 1.
DCT verwandelt den Block in ein Spektrum, und dort, wo die Messwerte scharf wechseln, wird der Koeffizient positiv, und je schärfer der Übergang, desto höher wird der Ausgang. Dort, wo der Koeffizient höher ist, sind im Bild deutliche Übergänge in Farbe und Helligkeit dargestellt, während er dort, wo er niedriger ist, schwache (sanfte) Veränderungen der Komponenten YCbCr im Block zeigt.
Quantisierung
Hier kommen bereits die Komprimierungseinstellungen zum Einsatz. Jeder der Koeffizienten in jeder der 8×8-Matrizen wird durch eine bestimmte Zahl geteilt. Wenn die Bildqualität nach all seinen Modifikationen nicht weiter verringert werden soll, sollte der Teiler eins sein. Wenn Ihnen der Speicherplatz, den dieses Foto beansprucht, wichtiger ist, wird der Teiler größer als 1 sein, und das Ergebnis wird gerundet. Es stellt sich heraus, dass nach dem Runden häufig viele Nullen entstehen.
Quantisierung wird verwendet, um die Möglichkeit einer noch höheren Kompression zu schaffen. So sieht es am Beispiel der Quantisierung der Kurve y = sin(x) aus:

Kompression
Zuerst durchlaufen wir die Matrix im Zickzack:

Wir erhalten ein eindimensionales Array mit Zahlen. Wir sehen, dass es viele Nullen darin gibt, die wir entfernen können. Statt einer Folge von vielen Nullen schreiben wir eine Null und danach die Anzahl der Nullen in der Folge. So kann die gesamte Array-Größe auf bis zu 1/3 reduziert werden. Danach komprimieren wir dieses Array mit dem Huffman-Verfahren und fügen es in die Datei ein.
Wo wird verwendet
Überall. Wie PNG wird JPEG in Kameras, Betriebssystemen (als Unternehmenslogos, App-Symbole, Thumbnails) und in allen Bereichen verwendet, in denen eine effiziente Speicherung von Bildern erforderlich ist.
Fazit
Derzeit sind Kenntnisse über JPEG nur zu Bildungszwecken von Wert, da es bereits überall integriert und von großen Gruppen optimiert wurde, die Grundlagen der Wissenschaft bleiben jedoch interessant.
Quellen
Quelle: habr.com
