Git селективный отменить локальные изменения из файла - PullRequest
140 голосов
/ 10 июля 2009

В моем git-репо, который отслеживает svn-репо, я внес несколько изменений в один файл.

Теперь я хочу отменить эти изменения (например, svn revert), но только части файла.

Я хочу иметь возможность просматривать различия в файле, отменять (отменять) изменения, которые мне не нужны, и сохранять изменения, которые я хочу.

git add -i 

Команда, кажется, имеет возможность сделать это, но я пока не хочу ставить это.

Ответы [ 6 ]

299 голосов
/ 05 марта 2010

Я считаю, что вы можете сделать это проще всего с:

git checkout -p <optional filename(s)>

С справочной страницы:

   −p, −−patch
       Interactively select hunks in the difference between the <tree−ish>
       (or the index, if unspecified) and the working tree. The chosen
       hunks are then applied in reverse to the working tree (and if a
       <tree−ish> was specified, the index).
       This means that you can use git checkout −p to selectively discard
       edits from your current working tree.
85 голосов
/ 10 июля 2009

Вы можете сделать это напрямую с помощью git checkout -p. См. ответ Даниэля Штутцбаха ниже.


Старый ответ (до введения checkout -p):

Вы можете сделать это так:

git add -i

(выберите туки, которые хотите сохранить)

git commit -m "tmp"

Теперь у вас есть фиксация только с теми изменениями, которые вы хотите сохранить, а остальные не установлены.

git reset --hard HEAD

На этом этапе незафиксированные изменения были отброшены, поэтому у вас есть чистый рабочий каталог, в котором вы хотите сохранить зафиксированные изменения.

git reset --mixed HEAD^

Это удаляет последний коммит ('tmp'), но сохраняет изменения в вашем рабочем каталоге без изменений.

РЕДАКТИРОВАТЬ: заменено --soft на --mixed, чтобы очистить область подготовки.

3 голосов
/ 10 июля 2009

Вы можете запустить git diff для файла, сохранить полученный diff, отредактировать его, чтобы удалить изменения, которые do хотите сохранить, затем запустить его через patch -R, чтобы отменить оставшиеся diff. 1005 *

git diff file.txt >patch.tmp
# edit patch.tmp to remove the hunks you want to keep
patch -R <patch.tmp
2 голосов
/ 10 июля 2009

Похоже, что вы хотите

 git revert --no-commit $REVSISON 

Затем вы можете использовать

 git diff --cached

, чтобы увидеть, какие изменения будут внесены до совершения (так как возврат - это просто фиксация в направлении вперед,повторяет обратное изменение в прошлом)

Если бы у вас был чистый Git-репозиторий, вы могли бы, в зависимости от ваших целей, использовать интерактивное перебазирование (git rebase -i), чтобы вернуться к коммиту, который вы не делалиНе нравится и не редактируйте коммит задним числом, чтобы изменения, которые вам не нравились, никогда не происходили, но это обычно только в том случае, если вы ЗНАЕТЕ , вы никогда больше не захотите его видеть.

1 голос
/ 10 июля 2009

Перечитывая вопрос, звучит так, как будто вы хотите отменить изменения, которые есть в вашем рабочем дереве, а не изменения, которые были зафиксированы ранее, но некоторые другие ответы заставляют его звучать так, будто мое чтение может быть неправильным. Вы можете уточнить?

Если изменения находятся только в вашей рабочей копии, то самый простой способ сделать это - внести изменения, которые вы хотите сохранить:

git add -i <file>

Затем отбросьте изменения, которые вы не хотите сохранять, проверив версию индекса:

git checkout -- <file>

Затем отмените внесение изменений, если вы не хотите, чтобы они были поставлены:

git reset -- <file>

Этот рецепт отменяет только выбранные изменения в файле (или файлах, которые вы указали) и не создает никаких временных фиксаций, которые затем необходимо отменить.

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

git reset <commit_before_first_unwanted_change> -- <file>

Затем вы можете следовать предыдущему рецепту git add -i <file>, чтобы поставить те изменения, которые вы хотите сохранить, git checkout -- <file>, чтобы отбросить нежелательные изменения, и git reset -- <file>, чтобы «удалить их».

0 голосов
/ 07 сентября 2015

Параметры командной строки, описанные в ответах здесь, удобны, когда файл находится на сервере, к которому я обращаюсь через терминал ssh.Однако, когда файл находится на моем локальном компьютере, я предпочитаю следующий способ:

Открыть файл в редакторе netbeans (который поставляется с поддержкой git).Netbeans помещает красные / зеленые / синие метки в номера строк, чтобы указать, где материал был удален / добавлен / изменен (соответственно).

Правый щелчок любой из этих меток дает вам возможность отменить это изменение.Кроме того, вы можете щелкнуть правой кнопкой мыши по красной и синей меткам, чтобы увидеть всплывающую версию старой версии.

...