Gitのファイル変更の取り消し(git checkout,git reset)について


はじめに

こんにちは。
この記事をご覧になられている方、初めまして。
プログラミングを勉強し始めて一か月ちょっとのものです。

今回は現在学習中の Git , Git Hub で私が特に悩んだ git checkout , git reset の仕組みの違いについて一部を
記載していこうと思います。

簡単な記事ではありますが、間違った点などありましたら、ご指摘お願いいたします。

では早速、行きましょう。

【悩んだ箇所】

Git Bash にて、ファイル変更を行い、その変更を取り消したものを cat コマンドにて確認しました。
git checkout コマンドでは変更は確認できましたが、git reset コマンドでは違いが確認できませんでした。

hogehoge.txt
#hogehoge.txtの中身を確認
$ cat hogehoge.txt
hogehoge
hogehoge2
#hogehoge.txtに「hogehoge3」を記載
$ echo "hogehoge3" >> hogehoge.txt
#上記の内容が反映されていることを確認
$ cat hogehoge.txt                                                                                                      
hogehoge
hogehoge2
hogehoge3
#git chekout 実施
$ git checkout hogehoge.txt
Updated 1 path from the index
#中身の確認
$ cat hogehoge.txt                                                                                                      
hogehoge
hogehoge2
#結果、変更が取り消されていることを確認できた
hogehoge.txt
#上記の状態より再度「hogehoge3」を記載して、stagingにあげる
$ echo "hogehoge3" >> hogehoge.txt
$ cat hogehoge.txt
hogehoge
hogehoge2
hogehoge3
$ git add hogehoge.txt
#git reset 実施
$ git reset hogehoge.txt
Unstaged changes after reset:
M       hogehoge.txt
#cat コマンドで確認
$ cat hogehoge.txt
hogehoge
hogehoge2
hogehoge3
#結果変化なし

【結論】

大きく分けて2点の誤解があることがわかりました。
① cat コマンド(Bashコマンド)による確認では、
 自分のPCで実際に操作できる箇所の内容しか見てない。
 今回のケースだと、 hogehoge.txt をメモ帳で開けた内容しか確認できない。
 (すいません、うまく言葉にできませんでした。)

② git checkout と git reset では、変更を取り消す際に参照している場所が異なるという点

以上二点が私の今回の誤解だったのですが、
②の要因が強いので、もう少し詳しく記載したいと思います。

Git の概要

まずは Git の大まかな概要から。
Git は分散型のバージョン管理で、モダンな技術を追われている方なら皆さん利用されているものと聞いています。

大体こんなイメージだと思います。
(また、Git , Git Hubの導入部分について記事の最後にいつも参考にさせていただいている方のYouTube動画リンクを張っておきます。)

変更取り消し参照先

git checkout , git reset の参照先ですが、
上記の図より、
git checkout は、Staging を参照して、Work Tree の変更を取り消します。
git reset は、ローカルリポジトリを参照して、Staging のみ変更を取り消します。

Work Treeはローカルで実際に皆さんが作業する場所の認識です。
なので、エクスプローラを開けて、ファイル作成したり、
ソースコードを実際に書き込んだりする場所と思っていただいていいです。

【結論】①にも繋がるのですが、 cat コマンドで「hogehoge.txt」の内容を確認していましたが、
これは Work Tree の状態を見に行っていると同義になります。

まとめ

以上より、git add により、Staging にあげた内容を git reset コマンドで変更を取り消しても
cat コマンドでいくら確認しようと、変更が確認できないわけです。
【理由】
cat コマンドは Work Tree の内容しか確認できないから

確認したいのであれば、git status になると思います。

hogehoge.txt
#Work Tree にのみ変更されている状態
$ git status                                                                                                            
On branch master
Your branch is up to date with 'origin/master'.

Changes not staged for commit:
  (use "git add <file>..." to update what will be committed)
  (use "git restore <file>..." to discard changes in working directory)
        modified:   hogehoge.txt

no changes added to commit (use "git add" and/or "git commit -a")
hogehoge.txt
#Staging まで変更をした状態
$ git add hogehoge.txt
$ git status
On branch master
Your branch is up to date with 'origin/master'.

Changes to be committed:
  (use "git restore --staged <file>..." to unstage)
        modified:   hogehoge.txt
hogehoge.txt
#ローカルリポジトリまで変更をした状態
$ git commit -m "qiita_3"
[master eff3bef] qiita_3
 1 file changed, 1 insertion(+)
$ git status
On branch master
Your branch is ahead of 'origin/master' by 1 commit.
  (use "git push" to publish your local commits)

nothing to commit, working tree clean

最後に

以上で今回の記事を終了します。
最後まで読んでいただいて、ありがとうございました。

またawsでの機械学習やPython学習で難しかったことの
アウトプット含めた共有などできればと思います。

Git , Git Hub の参考

Git , Git Hub について、
「サルでもわかる~」のサイトがあると思いますが、
難しくてわからないという人向けにある動画があります。
良ければこちらも見てください。