2015-01-21 2 views
2

저는 현재 git diff -M<limit>이 어떻게 작동하는지 파악하려고합니다.git diff -M은 어떻게 작동합니까?

내가 알아 낸 것은 git diff가 유사성 점수를 계산하여 유사한 두 파일 (수정본 1의 fileA, 수정 1, fileC)이 얼마나 유사한 지 확인합니다. 유사도 점수가> = limit 인 경우 fileA의 이름이 fileC으로 바뀌 었습니다 (점수가 < 100 % 인 경우).

그런 다음 디렉토리에 동일한 sha1 해시를 가진 파일이 더 있다면 어떻게해야합니까? git은 이름이 변경된 (변경된) 버전을 어떻게 알 수 있습니까? 7 개 라인 ("A", "B", "C", "D", "E", "F로

먼저 I 만든 두 파일 :

이 알고 싶다면, I는 다음 시도 ","g ")는

vi fileA 
vi fileB 

그러면 I 저장소에 추가하고 커밋 :

git add fileA fileB 
git commit -m "Added fileA and fileB" 

    [master ffc8964] Added fileA and fileB 
    2 files changed, 6 insertions(+) 
    create mode 100644 tests/fileA 
    create mode 100644 tests/fileB 

다음에, I는 git mv를 사용 fileCfileA 개명 01,238,685,535에서 첫 번째 행을 삭제및 fileC. 그 후 나는 지금과 같이 변경에게

git mv fileA fileC 
vi fileB 
vi fileC 
git commit -a -m "Renamed and changed files" 

    [master 57ff82a] Renamed and changed filed 
    2 files changed, 2 deletions(-) 
    rename tests/{fileA => fileC} (85%) 

fileBfileC을 최선을 다하고 :

b 
c 
d 
e 
f 
g 

내가 지금 예상 것은 fileBfileC의 체크섬이 동일하다고 :

git hash-object fileB fileC 
    9fbb6235d2d7eb798268d4537acebea297321241 
    9fbb6235d2d7eb798268d4537acebea297321241 

사실 그들은 다음과 같습니다 :-)

이제 git diff은 이름이 바뀐 파일이 무엇인지 알고 있어야합니까? fileC가 변경되었으므로 새로운 BLOB가 commit에 의해 생성되고 체크섬이 fileCfileA이 다릅니다 (분명히). .

git diff -M80% HEAD master~1 

출력은 그러나 분명히 git difffileAfileC로 이름이 변경되었다는 것을 알게 되었습니까

그러나 어떻게

diff --git a/tests/fileC b/tests/fileA 
similarity index 85% 
rename from tests/fileC 
rename to tests/fileA 
index 9fbb623..f9d9a01 100644 
--- a/tests/fileC 
+++ b/tests/fileA 
@@ -1,3 +1,4 @@ 
+a 
b 
c 
d 
diff --git a/tests/fileB b/tests/fileB 
index 9fbb623..f9d9a01 100644 
--- a/tests/fileB 
+++ b/tests/fileB 
@@ -1,3 +1,4 @@ 
+a 
b 
c 
d 

:-(나를 혼동 :

나는 그것을 시도? git이 fileAfileC 사이의 연결을 저장하지 않았습니까?

답변

2

이러한 연결이 저장되지 않았습니다. 한 파일이 삭제되고 다른 파일이 추가되면 이름 변경이 감지 될 수 있습니다. Git은 fileC이 새로 추가 된 것을보고 모든 삭제 된 파일을 검토하여 이름이 바뀌 었는지 확인합니다. 여기에서 삭제 된 파일은 fileA 이었으므로 다소 빠른 확인이었습니다.

참고 : 삭제 된 파일 만 이동하면됩니다. 그렇지 않으면 이름을 바꾸지 않아도됩니다. 사본도 감지 할 수 있으며 거의 ​​동일한 방식으로 작동하지만 별도의 옵션 (-C)이 적용됩니다.

+0

이것은 이름 바꾸기를 감지하기 위해'commit'을 상상하는 방법입니다. 그러나 'git diff'는 어떻게 알 수 있습니까? 두 커밋의 기록을 참조합니까? – Paddre

+0

@Paddre 커밋은 변경 내용을 저장하지 않고 새 트리를 저장합니다. 'git diff'와 같은 명령은 요구시 변경 사항을 계산합니다. 그래서'git diff'는 역사를 거치지 않고 두 커밋의 디렉토리와 파일에 즉시 액세스 할 수 있습니다. – hvd

+0

Thx (완벽한 의미로는 ... 어제 밤 내 마음에 무엇이 잘못되었는지 알지 못한다 : -P). 따라서'git diff'는 삭제 된 파일과 충분히 유사한 추가 된 파일이 있는지 확인합니다. 맞습니까? 그래서'git mv fileC fileD','cp fileD fileE','fileD'와'fileE','git add fileE'의 첫번째 줄을 삭제했습니다. 이제는 이름 바꾸기 (삭제 및 추가) 및 추가가 있었으며 이름이 바뀐 파일과 추가 된 파일 모두 동일한 체크섬을가집니다. 'git diff'는'fileD'가'fileC'의 이름이 바뀐 버전이라는 것을 아직도 어떻게 알 수 있습니까? – Paddre