Команда, которую вы ищете, это git rebase
, в частности параметр -i/--interactive
.
Я собираюсь предположить, что вы хотите оставить commit c на ветке A, и что вы действительно имеете в виду, что хотите переместить другие коммиты в другие ветви, а не слияния, поскольку слияния просты. Давайте начнем манипулируя ветвь A.
git rebase -i <SHA1 of commit a>^ branchA
^
означает, что предыдущий коммит, поэтому эта команда говорит перебазироваться ветвь А с использованием фиксации перед «а» в качестве базы. Git представит вам список коммитов в этом диапазоне. Reorder их и сказать ублюдка пережать подходящие из них:
pick c ...
pick a ...
squash d ...
squash e ...
squash g ...
pick b
squash f
Теперь история должна выглядеть следующим образом:
c - [a+d+e+g] - [b+f] (branchA)
/
--o-x-x-x-x-x-x-x-x-x-x (master)
Теперь, давайте захватить вновь раздавленный совершить б + п для branchB.
git checkout branchB
git cherry-pick branchA # cherry-pick one commit, the tip of branchA
И то же самое для + D + E + G для мастера:
git checkout master
git cherry-pick branchA^
Наконец, обновление branchA так указывает с:
git branch -f branchA branchA^^
Теперь мы должны иметь:
c (branch A) - [a+d+e+g] - [b+f] (dangling commits)
/
--o-x-x-x-x-x-x-x-x-x-x-[a+d+e+g] (master)
\
x-x-x-x-x-[b+f] (branchB)
Обратите внимание, что если у вас было несколько коммитов лет у хотел, чтобы перемещаться между ветвями, вы могли бы использовать перебазироваться снова (не в интерактивном режиме):
# create a temporary branch
git branch fromAtoB branchA
# move branchA back two commits
git branch -f branchA branchA~2
# rebase those two commits onto branchB
git rebase --onto branchB branchA fromAtoB
# merge (fast-forward) these into branchB
git checkout branchB
git merge fromAtoB
# clean up
git branch -d fromAtoB
Наконец, отказ от ответственности: Это вполне возможно, чтобы изменить порядок коммитов таким образом, что некоторые уже не применяются чисто. Это может быть связано с тем, что вы выбрали плохой порядок (установив патч перед фиксацией, введя исправленную функцию); в этом случае вы хотите прервать переустановку (git rebase --abort
).В противном случае вам придется разумно исправлять конфликты (как и при конфликтах слиянием), добавлять исправления, а затем запускать git rebase --continue
для перехода. Эти инструкции также предоставляются сообщением об ошибке, напечатанным при возникновении конфликта.
Два ответы уже даны Упоминание правильная команда, но я думаю, что с такой основной задачей, как эта, это стоит иметь настоящие инструкции здесь, в StackOverflow, поэтому я разместил некоторые. (Я удивлен, что не могу найти хороший предыдущий вопрос для ссылки.) – Cascabel