1220

を使用して、とgitk logの効果の違いを見つけることができませんでした。違いを確認するにはどうすればよいですか (git コマンドまたは何らかのツールを使用)。git mergegit merge --no-ff

4

8 に答える 8

1325

--no-ffフラグは、現在のコミットがマージしようとしているコミットの祖先であるgit mergeことを検出した場合、「早送り」の実行を防ぎます。HEAD早送りとは、マージ コミットを作成する代わりに、git がブランチ ポインターを移動して受信コミットを指すようにすることです。これは通常git pull、ローカルに変更を加えずに を実行した場合に発生します。

ただし、通常は特定のブランチ トポロジを維持したい場合 (たとえば、トピック ブランチでマージしていて、履歴を読み取るときにそのように見えるようにしたい場合など) に、この動作が発生するのを防ぎたい場合があります。--no-ffこれを行うには、フラグを渡すことができ、早送りの代わりに常にマージを構築しgit mergeます

git pull同様に、明示的に早送りするために a or useを実行したい場合git merge、および早送りできない場合に救済したい場合は、--ff-onlyフラグを使用できます。このようにして、考えずに定期的に何かを行うことができgit pull --ff-only、エラーが発生した場合は、戻ってマージするかリベースするかを決定できます。

于 2012-01-30T18:51:29.940 に答える
1245

この質問に対するグラフィックの回答

の使用に関する明確な説明とグラフィカルな図解があるサイトはgit merge --no-ff次のとおりです。

git merge --no-ff と git merge の違い

これを見るまで、私は git で完全に迷っていました。を使用--no-ffすると、履歴を確認している誰かが、作業のためにチェックアウトしたブランチを明確に見ることができます。(そのリンクは github の「ネットワーク」視覚化ツールを指しています) そして、ここにイラスト付きの別の素晴らしいリファレンスがあります。このリファレンスは、最初のリファレンスをうまく補完し、git にあまり詳しくない人に重点を置いています。


私のような初心者のための基本情報

あなたが私のようで、Git の第一人者ではない場合、ここでの私の回答では、ローカル ファイル システムからファイルを削除せずに、git の追跡からファイルを削除する処理について説明します。別の新しい状況は、現在のコードを取得することですが、それでも私を逃れています。


ワークフローの例

パッケージを自分の Web サイトに更新したので、メモに戻ってワークフローを確認する必要がありました。この回答に例を追加すると便利だと思いました。

git コマンドの私のワークフロー:

git checkout -b contact-form
(do your work on "contact-form")
git status
git commit -am  "updated form in contact module"
git checkout master
git merge --no-ff contact-form
git branch -d contact-form
git push origin master

下:説明を含む実際の使用法。
注: 以下の出力は省略されています。git は非常に冗長です。

$ git status
# On branch master
# Changed but not updated:
#   (use "git add/rm <file>..." to update what will be committed)
#   (use "git checkout -- <file>..." to discard changes in working directory)
#
#       modified:   ecc/Desktop.php
#       modified:   ecc/Mobile.php
#       deleted:    ecc/ecc-config.php
#       modified:   ecc/readme.txt
#       modified:   ecc/test.php
#       deleted:    passthru-adapter.igs
#       deleted:    shop/mickey/index.php
#
# Untracked files:
#   (use "git add <file>..." to include in what will be committed)
#
#       ecc/upgrade.php
#       ecc/webgility-config.php
#       ecc/webgility-config.php.bak
#       ecc/webgility-magento.php

上記の 3 つの点に注意してください
。1) 出力では、新しいファイルの追加を含む、ECC パッケージのアップグレードによる変更を確認できます。
2) また/ecc、この変更とは別に削除した 2 つのファイル (フォルダーにはありません) があることにも注意してください。これらのファイルの削除を と混同する代わりに、後でecc別のcleanupブランチを作成して、それらのファイルの削除を反映させます。
3) ワークフローに従わなかった! ecc を再び機能させようとしているときに、git のことを忘れていました。

以下: 通常はすべてを網羅するのではなく、フォルダーgit commit -am "updated ecc package"にファイルを追加するだけでした。/eccこれらの削除されたファイルは特に私の の一部ではありませんでしgit addたが、既に git で追跡されていたため、このブランチのコミットから削除する必要があります。

$ git checkout -b ecc
$ git add ecc/*
$ git reset HEAD passthru-adapter.igs
$ git reset HEAD shop/mickey/index.php
Unstaged changes after reset:
M       passthru-adapter.igs
M       shop/mickey/index.php

$ git commit -m "Webgility ecc desktop connector files; integrates with Quickbooks"

$ git checkout master
D       passthru-adapter.igs
D       shop/mickey/index.php
Switched to branch 'master'
$ git merge --no-ff ecc
$ git branch -d ecc
Deleted branch ecc (was 98269a2).
$ git push origin master
Counting objects: 22, done.
Delta compression using up to 4 threads.
Compressing objects: 100% (14/14), done.
Writing objects: 100% (14/14), 59.00 KiB, done.
Total 14 (delta 10), reused 0 (delta 0)
To git@github.com:me/mywebsite.git
   8a0d9ec..333eff5  master -> master



上記を自動化するスクリプト

このプロセスを 1 日に 10 回以上使用したので、コマンドを実行するバッチ スクリプトを作成するようになったのでgit_update.sh <branch> <"commit message">、上記の手順を実行するためのほぼ適切なスクリプトを作成しました。これがそのスクリプトの Gist ソースです。

git commit -am作成された「変更された」リストからファイルを選択してgit status、このスクリプトに貼り付ける代わりに。これは、数十回の編集を行ったが、変更をグループ化するのに役立つさまざまなブランチ名が必要だったために発生しました。

于 2013-02-14T00:08:21.747 に答える
42

これは古い質問であり、これは他の投稿でやや微妙に言及されていますが、私にとってこれをクリックした説明は、非早送りマージには別のコミットが必要になるということです。

于 2014-04-02T19:56:06.560 に答える
2

早送りとは?

早送りは、チェックアウトしたブランチの直前のブランチに対してマージまたはリベースするときに Git が行うことです。

次のブランチ設定があるとします。

両方のブランチが同じコミットを参照しています。どちらもまったく同じ歴史を持っています。今すぐ機能するものをコミットします。

master ブランチはまだ 7ddac6c を参照していますが、この機能は 2 つのコミットで進んでいます。フィーチャー ブランチは、マスターより先に考えられるようになりました。

Git が早送りを行ったときに何が起こるかを比較的簡単に確認できるようになりました。機能が実行する正確なコミットを参照するようにマスター ブランチを更新するだけです。機能からのコミットには必要なすべての変更が既に含まれているため、リポジトリ自体に変更は加えられません。

リポジトリの履歴は次のようになります。

早送りが発生しないのはいつですか?

元のブランチと新しいブランチで変更が行われた場合、早送りは行われません。

機能をマスターにマージまたはリベースすると、ツリーが両方とも分岐しているため、Git は早送りできません。Git コミットが不変であることを考慮すると、親参照を変更せずに Git がコミットを機能からマスターに取得する方法はありません。

于 2021-12-04T10:36:41.047 に答える