Почему репозитории Git / Mercurial занимают меньше места?

15

Я читал о нескольких обсуждениях здесь и о том, что репозитории DVCS используют примерно то же или меньше места, чем их централизованные компоненты. Возможно, я пропустил это, но я не нашел хорошего объяснения, почему это так. Кто-нибудь знает?

Алекс Флореску
источник
1
У меня нет, спасибо! Поэтому я понимаю, что есть два ответа: сжатие с использованием zlib и сохранение объектов в виде файлов пакетов, когда это возможно. Примеры из Mozilla тоже великолепны!
Алекс Флореску
1
@ Алекс Нет, это пропускает основную причину. SVN сохраняет полные снимки, Git и Mercurial сохраняют только ревизию HEAD и различия. Использование обычного сжатия может дать вам наилучший коэффициент сжатия около 60–80%. Использование различий может дать вам до 99%. Эти цифры вырваны из моей задницы, хотя - реальные цифры могут отличаться; тенденция будет такой же , хотя.
Конрад Рудольф
@KonradRudolph, разве это не пакетные файлы?
Алекс Флореску
@ Алекс Не совсем. Насколько я знаю, packfile дополнительно упаковывает несколько файлов в один. Это не обязательно связано.
Конрад Рудольф

Ответы:

18

Исходя из моего собственного опыта, все утверждения верны:

  • Git очень эффективен в хранении текстовых файлов и хранит только те файлы, которые были изменены. поэтому при сравнении SVN и Git для сравнения размеров репозитория они могут быть похожими или даже иметь небольшое преимущество для Git.
  • Это совершенно неверно, если сравнивать размер репозиториев, в которых значительное количество файлов представляет собой офисные файлы (например, MS Word, Excel, PowerPoint и т. Д.). Здесь Git также хранит полные копии, что означает, что 10 небольших изменений в стеке слайдов Powerpoint приводят к 10 полным копиям, где Subversion хранит только двоичные различия, которые могут быть в 100 раз меньше.

Если вы сравните местоположение извлечения (которое само по себе является хранилищем с Git), история будет совершенно другой:

  • Subversion хранит для каждого файла полную копию, поэтому размер вашего места оформления заказа обычно в 2 раза больше размера самих файлов.
  • Git хранит полную историю хранилища локально, поэтому, в зависимости от размера истории, она может быть меньше или намного больше, чем у копии извлечения Subversion.

Если вы сравните количество байтов, которое вам нужно загрузить или загрузить, оно снова будет другим.

  • Обычно Subversion отправляет или получает меньше байтов, потому что отправляет только различия. Он должен делать это при каждом коммите и обновлении.
  • Git должен получить весь репозиторий (изначально), а затем отправляет полные файлы (сжатые?), Которые не сильно отличаются для текстовых файлов, но могут отличаться для двоичных файлов. И да, Git делает это только тогда, когда вы что-то толкаете или переносите в удаленный репозиторий.

Итак, в конце вы сравниваете яблоки с апельсинами, и в зависимости от того, что вы хотите сделать с Subversion или Git, результат может быть другим.


@jk спросил о полных копиях или бинарных разностях, и я не смог ответить на этот вопрос. Я спросил Мэтью МакКаллоу, который недавно проводил семинар по Git на Jax 2012 (который я посетил). Он потратил время (большое ему спасибо), чтобы подробно объяснить суть внутренней работы Git. Так что да, там работает сжатие (и я также проведу эксперимент с офисным файлом Microsoft и сравню это с его сущностью), но нет, сжатие выполнено для всего файла. Ссылаясь на его суть:

Свободные объекты записываются в сжатом, но не дельта-формате во время каждой фиксации.

mliebelt
источник
1
Вы уверены, что git хранит полные копии офисных файлов? Я думаю, что он также хранит двоичные различия. Конечно, проблема таких файлов в том, что они часто уже сжаты, поэтому небольшое изменение может привести к изменению всего файла
jk.
2
Спросил кого-то (по электронной почте), который знает гораздо больше, чем я, и включит свой ответ в мой ответ.
mliebelt
6
Git обрабатывает текстовые и двоичные файлы одинаково во всех отношениях и в отношении хранения. Свободные и упакованные объекты не связаны с текстовыми и двоичными файлами. Причина, по которой двоичные файлы часто приводят к гораздо большим различиям, чем текстовые файлы, заключается в том, что многие двоичные форматы (включая все новые офисные форматы) уже сжаты, и, таким образом, даже небольшое изменение в содержимом часто вызывает большие изменения в полученном двоичном двоичном объекте. Это в равной степени относится и к git, и к subversion, но subversion берет на себя штраф только за сервер, а git везде.
Ян Худек
4
Свободные и упакованные объекты не имеют ничего общего с текстом против двоичного. Это амортизация сложной работы по нахождению бинарных различий. Скорость - важная особенность git, поэтому во время обычной работы git только архивирует новые данные и помещает их в хранилище. Это незакрепленные предметы. Затем, когда вы обращаетесь к нему, вызывая git gcили накапливая слишком много незакрепленных объектов, он находит подходящих кандидатов для их дельта-сжатия (git может отличаться от предыдущей версии), сохраняет дельты в «пакете» и удаляет незакрепленные объекты.
Ян Худек
3
Для тех, кто интересуется реальными цифрами: я просто сравнил две рабочие копии из одного и того же репо. Рабочая копия SVN составляет около 2,9 ГБ, рабочая копия GIT - около 0,8 ГБ.
JensG