Путаница между контейнером и кодеком встречается постоянно: человек скачивает файл с расширением mkv, видит рядом название H.264 и решает, что это два синонима одного и того же формата. На деле это два независимых слоя, которые решают разные задачи и вообще не обязаны идти в паре. Контейнер отвечает за то, как данные упакованы в файл, а кодек, за то, каким алгоритмом эти данные были сжаты внутри. Разобраться в этой разнице полезно не только для общей эрудиции: от неё напрямую зависит, почему один файл воспроизводится на телевизоре, а другой выдаёт ошибку, и почему конвертация между форматами иногда занимает секунды, а иногда часы.

Что такое контейнер и зачем видеофайлу вообще нужна такая обёртка

Контейнер, или контейнерный формат, это структура файла, которая описывает, как внутри него организованы разные потоки данных: видеодорожка, одна или несколько звуковых дорожек, субтитры, обложка, метаданные о таймкодах и синхронизации. Сам по себе контейнер ничего не сжимает и не решает, насколько компактным получится видео, он лишь задаёт правила упаковки уже сжатых потоков в единый файл и правила их совместного воспроизведения. Именно поэтому размер готового файла определяется в первую очередь кодеком, битрейтом и разрешением, а не выбором контейнера: два одинаковых видеопотока, упакованные в разные контейнеры при прочих равных параметрах, займут почти одинаковый объём на диске.

Распространённые контейнеры, MP4, MKV, AVI, WebM, ASF, отличаются друг от друга не столько принципом работы, сколько набором возможностей и ограничений: сколько дорожек можно уместить в одном файле, какие кодеки разрешены спецификацией, насколько гибко хранятся метаданные и насколько устойчив формат к повреждению отдельных частей файла. Формат AVI, один из старейших массовых контейнеров, устроен предельно просто и не хранит часть служебной информации вроде точных пропорций пикселя, из-за чего плеерам иногда приходится угадывать параметры воспроизведения самостоятельно. Более новые форматы вроде MP4 и MKV решают эту проблему за счёт более подробной и структурированной службы метаданных.

Накладные расходы самого контейнера на общий размер файла обычно ничтожны по сравнению с весом сжатого видеопотока. Служебная структура контейнера, таблицы индексов для быстрой перемотки, теги с названием и описанием, информация о таймкодах кадров, как правило занимает от нескольких десятков до нескольких сотен килобайт даже для полнометражного фильма весом в несколько гигабайт, то есть заметно меньше одной десятой процента от общего размера файла. Отсюда следует важный практический вывод: смена контейнера сама по себе почти никогда не даёт заметной экономии места, вся реальная экономия достигается именно на уровне кодека и подобранного для него битрейта.

Что такое кодек и почему H.264 занимается исключительно сжатием изображения

Кодек, сокращение от кодировщика-декодировщика, это программно реализованный алгоритм, который превращает исходный видеопоток в компактное представление и умеет затем восстанавливать из него картинку обратно. H.264, также известный под названием AVC, один из самых распространённых видеокодеков в мире: он делит каждый кадр на блоки, ищет избыточность внутри одного кадра и между соседними кадрами, применяет частотные преобразования и квантование, а затем упаковывает результат с помощью энтропийного кодирования. Кодек не имеет никакого отношения к тому, как готовый сжатый поток будет разложен по файлу, синхронизирован со звуком или проиндексирован для перемотки, это работа исключительно контейнера.

Именно поэтому один и тот же поток, сжатый кодеком H.264, физически может лежать внутри файла MP4, MKV, AVI, TS или ещё десятка других контейнеров без единого бита изменений в самих видеоданных. Ситуация симметрична и для звука: кодек MPEG-4 может применяться для сжатия видеопотока сразу в нескольких разных контейнерах, включая MP4, MKV, MXF, OGG и QuickTime, и от выбора контейнера сам алгоритм сжатия внутри не меняется ни на йоту. Разница проявляется только в том, какие метаданные, дополнительные дорожки и удобства получает пользователь вокруг этого сжатого потока.

Как устроен формат Matroska изнутри и почему он называется коробкой для видео

Контейнер Matroska, известный по расширению mkv, был анонсирован 6 декабря 2002 года как ответвление от более раннего проекта Multimedia Container Format, после расхождения во мнениях среди разработчиков относительно использования расширяемого бинарного языка разметки EBML вместо обычного бинарного формата. Именно на EBML построена вся внутренняя структура Matroska: файл организован как дерево вложенных элементов переменной длины, что делает формат гибким и устойчивым к добавлению новых типов данных без поломки совместимости со старыми проигрывателями. Сегодня формат стандартизирован как открытый документ RFC 9559, а актуальная версия спецификации, четвёртая (v4), поддерживается сообществом разработчиков без привязки к какой-либо одной коммерческой компании.

Главная особенность Matroska, ради которой формат и получил прозвище "матрёшка", это способность вмещать в один файл неограниченное число видео-, аудио-, графических дорожек и дорожек субтитров одновременно. Именно поэтому в одном файле mkv нередко можно найти сразу несколько звуковых дорожек на разных языках, комментарии авторов, встроенные субтитры сразу нескольких типов и даже обложку альбома или постер фильма в виде отдельного вложения. Контейнер практически не ограничивает разработчиков в выборе кодека: внутри mkv одинаково хорошо уживаются H.264, H.265, старые кодеки вроде MPEG-2, а также звуковые форматы AC3, DTS, FLAC и множество других, которые для некоторых конкурирующих контейнеров попросту недоступны по официальной спецификации.

Почему формат MP4 жёстче ограничивает набор допустимых кодеков внутри себя

Контейнер MP4 появился как открытый стандарт в 2001 году и со временем пришёл на смену закрытому формату QuickTime, у которого он заимствовал часть базовой структуры. По умолчанию спецификация MP4 куда строже описывает допустимые типы дорожек, чем открытая и гибкая Matroska: для звука официально предусмотрена в первую очередь поддержка кодека AAC, тогда как многие другие звуковые форматы, привычные для DVD и Blu-Ray дисков вроде AC3, формально выходят за рамки базовой спецификации. Это создаёт неудобство при переносе многоканального звука из более старых источников: чтобы уложиться в ограничения MP4, звуковую дорожку иногда приходится заново перекодировать в AAC, а любое повторное кодирование звука или видео с потерями означает дополнительное, пусть и небольшое, ухудшение качества по сравнению с оригиналом.

Зато именно строгость и предсказуемость MP4 стали причиной его повсеместного распространения на мобильных устройствах, в браузерах и на стриминговых платформах: узкий и хорошо документированный набор поддерживаемых кодеков гораздо проще реализовать в аппаратном декодере смартфона или телевизора, чем универсальный парсер, способный справиться с любой комбинацией потоков, которую в теории может содержать файл Matroska. Отсюда и практическое правило, которое интуитивно выработали пользователи: MP4 предпочтителен там, где важна максимальная совместимость с разными устройствами, а MKV, там, где важна гибкость, многодорожечность и работа с архивами, которые не обязаны воспроизводиться на любом устройстве без исключения.

Отдельного упоминания заслуживает контейнер TS, широко применяемый в цифровом телевещании и потоковой передаче через интернет. В отличие от MP4 и MKV, рассчитанных на цельный файл с заранее известным размером, TS проектировался для непрерывного потока, который можно начать смотреть с произвольного места без полной загрузки, а также устойчив к обрыву связи: даже частичная потеря фрагмента потока не мешает продолжить чтение и воспроизведение оставшихся данных. Кодек внутри TS чаще всего тот же самый H.264 или H.265, что и в MP4, но именно устройство контейнера делает формат пригодным для прямых эфиров, тогда как MP4 и MKV лучше подходят для готовых файлов с известным заранее объёмом.

Что происходит при перепаковке видео между контейнерами без повторного сжатия

Раз кодек и контейнер это независимые слои, значит переложить уже сжатый видеопоток из одного контейнера в другой можно вообще без обращения к самому алгоритму сжатия, если оба контейнера поддерживают используемый кодек. Такая операция называется перепаковкой, или ремуксингом: программа просто извлекает готовые сжатые дорожки из старой обёртки и укладывает их в новую, попутно пересобирая метаданные и таблицы синхронизации, но не трогая ни единого байта самого видео- или аудиопотока. Именно поэтому перепаковка занимает считаные секунды даже для файла на несколько гигабайт: типичная команда вроде вызова ffmpeg с параметром copy для видео- и аудиопотока перекладывает данные практически со скоростью чтения и записи диска, без единого обращения к декодеру или энкодеру.

Совсем другая ситуация возникает, если целевой контейнер не поддерживает исходный кодек или пользователю нужно сменить сам алгоритм сжатия, например перевести видео из H.264 в H.265 ради экономии места. Тогда потребуется полноценное перекодирование, транскодинг: сначала декодер полностью восстанавливает изображение кадр за кадром, а затем новый кодек заново сжимает эту картинку своим собственным алгоритмом с нуля. Разница в скорости между этими двумя сценариями колоссальна: в отдельных практических замерах перекодирование в браузере через программный декодер шло со скоростью около девяти кадров в секунду, тогда как простая перепаковка того же материала без смены кодека укладывалась в считаные секунды независимо от общей длины ролика, что в пересчёте на кадры в секунду отличается на два порядка. Ремуксинг также никогда не ухудшает качество, поскольку не затрагивает сжатые данные, а транскодинг почти всегда добавляет дополнительные потери, характерные именно для алгоритма сжатия с потерями, каким является H.264.

Как выбрать разумное сочетание контейнера и кодека под конкретную задачу

Понимание разницы между двумя слоями формата упрощает практические решения, с которыми сталкивается почти каждый, кто работает с видео регулярно:

  1. для хранения архивных копий и рипов с несколькими звуковыми дорожками и субтитрами разумнее выбирать MKV, поскольку формат не ограничивает набор кодеков и позволяет уместить максимум сопутствующей информации в одном файле;
  2. для публикации ролика в интернете или отправки на мобильное устройство надёжнее упаковывать сжатое видео в MP4, потому что узкий и предсказуемый набор поддерживаемых кодеков даёт наилучшую совместимость с браузерами и аппаратными декодерами;
  3. при простом переносе готового видео между контейнерами без необходимости менять качество или разрешение стоит искать инструмент, который умеет перепаковку без повторного сжатия, поскольку это происходит на порядки быстрее полноценного перекодирования и не портит исходное качество;
  4. при выборе именно кодека, а не контейнера, стоит отталкиваться от вычислительных возможностей устройства воспроизведения, поскольку H.265 экономит место при равном качестве картинки, но требует заметно больше ресурсов процессора для декодирования, чем более простой и универсальный H.264.

Такое разделение ответственности между контейнером и кодеком объясняет и типичные ошибки при работе с видео: попытка "открыть кодеком" файл вместо программы для воспроизведения, жалобы на то, что "формат mkv не поддерживается", когда на самом деле проблема в конкретном кодеке внутри файла, или недоумение по поводу того, почему смена расширения файла с mkv на mp4 вручную не работает и портит видео вместо того, чтобы просто изменить обёртку. Контейнер и кодек живут своей отдельной жизнью, и только понимание этой границы позволяет точно определить, что именно нужно менять, чтобы решить конкретную проблему с воспроизведением или размером файла.