Подтвердить что ты не робот

Плюсы и минусы различных моделей ветвления в DVCS

Большая тройка распределенного контроля версий (Git, Bazaar и Mercurial) каждый рассматривает ветвление довольно по-разному. Например, в Bazaar ветки представляют собой отдельные репозитории (фактически, расходящиеся копии родительского репо); в вашей файловой системе разные ветки живут в разных каталогах. В Git, с другой стороны, вы можете иметь несколько ветвей, существующих в одном и том же репо (и, следовательно, в том же каталоге в вашей файловой системе). Mercurial поддерживает оба поведения, последний с назвал ветки.

Каковы плюсы и минусы, связанные с этими разными ветвящимися моделями? На мой взгляд, подход Bazaar одной ветки, один репо делает больнее больнее, чем подход Git (например, чтобы использовать ветку на базаре, я должен сначала создать ветвь, затем cd из моей текущей рабочей копии, затем проверьте новую ветку, как я бы в SVN).

4b9b3361

Ответ 1

Bazaar не требует, чтобы вы работали так, как вы описываете. Я фактически написал сообщение в блоге об этом два дня назад. Вы можете работать в основном только с одним рабочим деревом, переключаясь между различными ветвями и создавая новые ветки, не выходя из рабочего дерева. Полезными командами для этого являются: checkout, switch, branch --switch. Просмотрите workflow документацию для Bazaar, вы увидите, что вы можете настроить ее практически любым способом.

Ответ 2

Я не очень разбираюсь в ветвящихся моделях в VCS, кроме Git. Я бы сказал, что в любом DVCS вы можете реализовать ветвление путем клонирования (вы создаете ветвь, выполняя клон). Меркуриальные так называемые "названные ветки" (из того, что я понимаю) на самом деле фиксируют метки, которые интерпретируются как ветка, иногда требующая локальной нумерации ревизий для устранения двусмысленности. Mercurial "bookmarks" ar, я думаю, очень похож на ветки Git. Два DVCS, которые имеют совершенно различную концепцию ветвления, Monotone и Darcs. Я думаю, что "разветвление путем копирования", которое использует Subversion, где разделение между именем проекта и именем ветки условно, является неправильной идеей.


В версиях Git образуется направленный ациклический граф (DAG) коммитов. Это направлено, потому что у коммиттов есть родители. Это очень важная проблема: края в DAG коммитов - от фиксации к ее родительскому объекту (или, в случае слияния, двух или более родителей). График фиксации ацикличен, что означает, что нет цепи (без пути), которая начинается и заканчивается одним и тем же объектом.

Git глоссарий определяет "ветвь" как активную линию развития . Эта идея стоит за реализацией ветвей в Git.

Самая последняя фиксация на ветке называется подсказкой этой ветки. Наконечник ветки ссылается на ветвь ветки, которая является просто символическим именем для этой фиксации. В своей "свободной" форме такая ветвь ветки (например, для ветки с именем "master" ) - это просто файл где-то в директории refs/heads/ внутри репозитория Git (внутри .git dir), который содержит ссылку на текущий совет branch: его идентификатор SHA-1 commit (как шестнадцатеричная строка).

Когда вы создаете новый фиксатор в Git, кончик текущей проверенной ветки движется вперед. Другими словами, новая фиксация создается поверх вершины текущей ветки, а ветвь ветки переходит к новому фиксации (несколько аналогично тому, как может продвигаться указатель на вершину стека).

Единственный репозиторий Git может отслеживать произвольное количество ветвей, но ваше рабочее дерево (если оно есть) связано только с одним из них (ветвь "текущая" или "вывешенная" ). Текущая ветвь указана указателем HEAD. HEAD - это (обычно) указатель на текущую проверенную ветку (на название головки ветки), так же как ветки ветвей являются указателями на концы ветвей.

Например, если в настоящий момент отмечена ветка "master", тогда .git/HEAD файл (представляющий HEAD) будет содержать одиночную линию с завершенным LF с ref: refs/heads/master (символическая ссылка на refs/heads/master) и .git/refs/heads/master (head раздела "master" ) будет содержать, например, LF-завершенную строку 0b127cb8ab975e43398a2b449563ccb78c437255, которая является идентификатором SHA-1 в конце ветки "master" (то есть, если текущая ветка не "упакована" ), тогда вы должны взглянуть на .git/packed-refs).

Некоторые команды в Git, такие как "git commit" или "git reset" манипулируют/меняют голову ветки; другие, такие как "git checkout", манипулируют/меняют HEAD (символическая ссылка на текущую ветку).

Команда

"git log branch" показывает все фиксированные цели с кончика ветки, что означает подсказку ветки, ее родителя, родителя (или родителей) этого родительского коммита и т.д. Он показывает часть DAG коммитов.

В Git удаление ветки означает просто удаление ветки ветки. Это может означать, что некоторые коммиты становятся "невидимыми", недоступными refom refs (ветки и теги), а это означает, что в какой-то момент эти коммиты могут получить мусор, собранный и удаленный из репозитория. Но если вы можете удалить ветвь с "git branch -d <branchname> " то это означает, что никакие коммиты не будут потеряны; вы можете принудительно удалить ветвь с ветвью git -D <branchname> ". Переименование ветки - это просто вопрос переименования ветки ветки, символической ссылки (символического имени) кончика ветки; имена ветвей не сохраняются нигде в объекте commit.


Git имеет также концепцию reflogs, которая является локальной историей, где указатель ветки указывает (и когда). Например, если вы измените фиксацию с помощью "git commit -amend", ответ ветки будет заменен измененным фиксацией, а HEAD ^ будет родителем фиксации до и после внесения изменений, тогда как будет запись в reflog для версии до внесение поправок и внесение поправок. Если вы перемотаете историю, используя "git reset", reflog будет содержать информацию старого кончика ветки перед перемоткой.

Вкратце reflog дает дополнительную безопасность и простое восстановление команд Git.