파일 끝에 줄 바꿈이 없습니다.


472

를 수행 할 때 git diff그것은 말한다 "파일의 마지막에 개행 문자가" .

좋아, 파일 끝에 줄 바꿈이 없습니다. 큰 문제는 무엇입니까?

이 메시지의 의미는 무엇이며 우리에게 무엇을 말하려고합니까?


11
아마도 줄 바꿈없이 끝나는 파일이 있고 다른 줄을 추가하면 git은 줄 바꿈 문자가 줄의 일부로 포함되어 있기 때문에 이전 마지막 줄이 변경되었음을 보여 주어야합니까?
nafg

답변:


458

'\n'파일 끝에 줄 바꿈 (일반적으로 CR 또는 CRLF) 이 없음을 나타냅니다 .

즉, 간단히 말하면 파일의 마지막 바이트 (또는 Windows의 경우 바이트)는 줄 바꿈이 아닙니다.

그렇지 않으면 마지막에 줄 바꿈이있는 파일과 그렇지 않은 파일 사이의 차이를 구분할 방법이 없기 때문에 메시지가 표시됩니다. Diff는 어쨌든 개행을 출력해야합니다. 그렇지 않으면 결과를 자동으로 읽거나 처리하기가 더 어려워집니다.

파일 형식에서 허용되는 경우 항상 줄 바꿈을 마지막 문자로 두는 것이 좋은 스타일입니다. 또한, 예를 들어 C 및 C ++ 헤더 파일의 경우 언어 표준에 필요합니다.


136
호기심으로, 항상 마지막 문자로 줄 바꿈을하는 것이 왜 좋은 스타일로 간주되는지 설명 할 수 있습니까? 편집 : 이 토론을 찾았습니다 .
Paul Bellora 2011

84
@PaulBellora 역사적으로 C 언어 표준 stackoverflow.com/a/729725/233098에 의해 결정되었습니다. 실제로 많은 유닉스 도구가 적절한 표시를 위해 필요하거나 기대하기 때문에 stackoverflow.com/a/729795/233098 입니다. 철학적으로 텍스트 파일의 각 줄은 "줄 끝"문자로 끝나기 때문에 마지막 줄도 예외는 아닙니다. 다르게 생각하면 그 반대를 살펴 봅시다. "줄 끝"대신 "줄 시작"마커가있는 경우 첫 번째 줄에서 "줄 시작"문자를 생략 하시겠습니까?
Joe

29
@Joe 그다지 말이되지 않습니다. 줄 바꿈은 줄 바꿈이 아닌 사이의 구분 기호 인 줄 바꿈입니다. 우리는 줄 문자가 필요하지 않기 때문에 시작 문자가 없습니다. 같은 이유로 줄 끝 문자가 없습니다.
acjay

6
@acjay 나는 "줄 사이의 구분자"와 "줄의 끝"사이에 본질적으로 더 낫다고 주장한다. 어떤 관점도 본질적으로 옳고 그른 것이 아니라 그것을 보는 한 가지 방법 일뿐입니다. 나는 우리가 포인트의보기 우리는 이미 그런 식으로 일을하고 있기 때문에, 역사적으로 실용적 계속 사용하고 제안하고있어 않습니다 당신이 그것을 받아 들일 때 메이크업 감각. 일관성이 중요합니다. "선 사이의 구분자"관점에서 그 이름을 깰 필요는 없습니다.

17
@WORMSS "New to me"는 "새로운 규칙"과 다릅니다. 이것은 다른 종류의 프로그래밍 규칙을 발견하는 것과 같습니다. 당신은 그것으로 간다. 당신 벗어날 있지만, 당신은 자신을 고립시키고 있습니다. (또는이 경우 실제로 도구를 깨뜨리는 경우도 있습니다.) 다른 많은 사람들이 Rails 컨벤션 또는 PEP8을 발견 한 이유와 그에 반해 코드를 작성 했음에도 불구하고 커뮤니티가 제공 한 전체가 얼마나 일관성이 있는지 생각해보십시오.
Joe

100

나쁜 스타일 일뿐 만 아니라 파일에서 다른 도구를 사용할 때 예기치 않은 동작이 발생할 수 있습니다.

여기 있습니다 test.txt:

first line
second line

마지막 줄에는 줄 바꿈 문자가 없습니다. 파일에 몇 줄이 있는지 봅시다 :

$ wc -l test.txt
1 test.txt

어쩌면 그것이 원하는 것일 수도 있지만 대부분의 경우 파일에 2 줄이있을 것으로 예상합니다.

또한 파일을 결합하려는 경우 예상대로 작동하지 않을 수 있습니다.

$ cat test.txt test.txt
first line
second linefirst line
second line

마지막으로 새 줄을 추가하면 diff가 약간 더 시끄 럽습니다. 세 번째 줄을 추가 한 경우 새 줄뿐만 아니라 두 번째 줄에 대한 편집 내용이 표시됩니다.


4
cat의 결과는 정상이지만 wc 매개 변수 "-l, --lines"는 잘못되었습니다. 매뉴얼에서도 "줄 바꿈 인쇄"가 아니라 "줄 바꿈 카운트 인쇄"라고 말합니다.
놀라운 1

그리고 나는 최근 util linux (util-linux 2.34)로 이것을 (wc와 cat) 재생할 수 없습니다.
wget을

1
@ wget 나는 util-linux 2.34를 사용하고 있으며이 답변이 현재 행동이라는 것을 확인할 수 있습니다. 내 생각 엔 편집자가 "\ n"문자를 추가 한 것 같습니다.
stephanos

29

유일한 이유는 유닉스가 역사적으로 개행 문자로 끝나는 사람이 읽을 수있는 모든 텍스트 파일의 규칙을 가지고 있기 때문입니다. 당시에는 텍스트 파일을 표시하거나 결합 할 때 추가 처리를 피하고 다른 종류의 데이터 (예 : 사람이 읽을 수없는 원시 이진 데이터)가 포함 된 파일과 다르게 텍스트 파일을 처리하지 않았습니다.

이러한 규칙으로 인해 당시의 많은 도구는 텍스트 편집기, diffing 도구 및 기타 텍스트 처리 도구를 포함하여 줄 바꿈 줄을 기대합니다. Mac OS X은 BSD Unix를 기반으로 구축되었으며 Linux는 Unix와 호환되도록 개발되었으므로 두 운영 체제 모두 동일한 규칙, 동작 및 도구를 상속받습니다.

Windows는 Unix와 호환되도록 개발되지 않았으므로 동일한 규칙이 없으며 대부분의 Windows 소프트웨어는 줄 바꿈없이 잘 처리됩니다.

그러나 Git이 먼저 Linux 용으로 개발되었고 Linux, Mac OS X, FreeBSD 등과 같은 Unix 호환 시스템에 많은 오픈 소스 소프트웨어가 구축되었으므로 대부분의 오픈 소스 커뮤니티 및 해당 도구 (프로그래밍 언어 포함)는 계속됩니다 이 규칙을 따라야합니다.

1971 년에 의미가있는 기술적 인 이유가 있지만이 시대에는 기존 도구와의 호환성을 유지하는 것이 관례입니다.


23

기존 파일의 끝에 아직 끝에 없는 새 텍스트 줄 을 추가 newline character하면 diff는 개념적으로 그렇지 않더라도 이전 마지막 줄이 수정 된 것으로 표시합니다.

이것이 newline character끝에 추가해야하는 최소한 하나의 이유 입니다.

파일은 다음을 포함합니다 :

A() {
    // do something
}

Hexdump에서는 :

00000000: 4128 2920 7b0a 2020 2020 2f2f 2064 6f20  A() {.    // do 
00000010: 736f 6d65 7468 696e 670a 7d              something.}

당신은 지금 그것을 편집

A() {
    // do something
}
// Useful comment

Hexdump에서는 :

00000000: 4128 2920 7b0a 2020 2020 2f2f 2064 6f20  A() {.    // do 
00000010: 736f 6d65 7468 696e 670a 7d0a 2f2f 2055  something.}.// U
00000020: 7365 6675 6c20 636f 6d6d 656e 742e 0a    seful comment..

git diff는 다음을 보여줍니다.

-}
\ No newline at end of file
+}
+// Useful comment.

즉, 개념적으로 발생하는 것보다 더 큰 차이를 보여줍니다. 그것은 당신이 라인을 삭제 한 것을 보여준다 }와 라인을 추가 }\n. 이것은 실제로 일어난 일이지만 개념적으로 일어난 일은 아니므로 혼란 스러울 수 있습니다.


2
우리는 다른 방향으로 같은 것을 쓸 수 있습니다 : 이미 줄 바꿈이있는 기존 파일의 끝에서 새 줄을 제거하면 diff는 개념적으로 그렇지 않을 때 수정 된 것처럼 오래된 마지막 줄도 표시합니다. 마지막에 개행을 제거해야하는 최소한 한 가지 이유.
gentiane

3
@gentiane "새 줄"(새 줄)과 "줄 바꿈"(줄 끝을 구분하는 1 ~ 2 자)을
혼동하고 있습니다.

@minexew 아니요, gentiane은 아닙니다. "새 줄"이 "새 줄"과 동일하다는 것을 모르실 수도 있습니다.
놀라운 1

3
@TheincredibleJan 답에 사용 된 두 용어는 서로 다른 의미를 갖습니다. 나는 당신이 현명한 엉덩이가 되려고 노력하고 있는지 또는 무슨 일이 일어나고 있는지 오해하고 있는지 모르겠습니다.
minexew

18

파일 끝에 줄 바꿈이 없음을 나타냅니다. 그것은 명령 줄에서 DIFF 볼 때 하나가 아니라는 것을 그것을 명확하게 그냥 메시지의 재앙이 아니다.


10

이 규칙이 실행 된 이유는 UNIX 계열 운영 체제에서 줄 바꾸기 문자가 줄 종결 자 및 / 또는 메시지 경계로 처리되기 때문입니다 (프로세스 간 연결, 줄 버퍼링 등).

예를 들어, 개행 문자 만있는 파일은 하나의 빈 줄로 취급됩니다. 반대로, 길이가 0 바이트 인 파일은 실제로는 줄이 0 인 빈 파일입니다. wc -l명령 에 따라 확인할 수 있습니다 .

\n문자가 단순히 줄 종결자가 아닌 줄 구분자 인 경우 빈 텍스트 파일과 빈 줄이 하나있는 텍스트 파일을 구분하는 다른 방법이 없기 때문에이 동작은 합리적 입니다. 따라서 유효한 텍스트 파일은 항상 개행 문자로 끝나야합니다. 텍스트 파일이 비어있는 경우 (행 없음)는 예외입니다.


1
왜 다운 보트를 받습니까 -2? 다른 답변에 명시된 내용 (예 : 표준 UNIX 기반 도구는 줄 바꿈 문자로 줄 바꿈을 기대 함)을 확인할뿐만 아니라 빈 파일을 하나의 빈 줄과 구별 할 수있는 방법이 없다는 것을 지적했습니다. . 나는 구체적으로 "메시지의 중요성은 무엇이며 우리에게 무엇을 말하려고합니까?"
Leslie Krause

나는 당신을 줄이지 않았지만이 응답은 줄 바꿈이 줄 바꿈 문자 일 때만 적용된다는 점에서 Unix 유형 시스템에만 적용되는 것으로 보입니다. 그것이 여기에 적용되는지 확실하지 않습니다. 또한 파일이 빈 줄로 구성된 경우 경고가 쓸모없는 것처럼 보입니다. 그러나 사람들은 종종 설명없이 downvote하기 때문에 Stackoverflow를 피합니다.
user34660

9

이전 답변에서 볼 수없는 것이 있습니다. 줄 끝이 없다는 경고는 파일의 일부가 잘 렸을 때 경고가 될 수 있습니다. 데이터가 누락 된 증상 일 수 있습니다.


일반적으로 좋은 지적이지만이 특정 질문의 맥락에서 의미가 있다고 생각하지 않습니다.
cst1992

@ cst1992 Stackoverflow의 답변은 가능한 한 유용해야하므로 모든 가능성에 적용되어야합니다. 질문은 짧고 내가 제안한 가능성을 배제하는 곳을 알 수 없습니다.
user34660

7

핵심 문제는 줄을 정의하는 것과 줄 끝 문자 시퀀스가 ​​줄의 일부인지 여부입니다. UNIX 기반 편집기 (예 : VIM) 또는 도구 (예 : Git)는 EOL 문자 시퀀스를 줄 종결 자로 사용하므로 줄의 일부입니다. C와 Pascal에서 세미콜론 (;)을 사용하는 것과 비슷합니다. C 세미콜론에서는 명령문이 종료되고 파스칼에서는 명령문이 분리됩니다.



3

소스 파일은 도구 (C, C ++ : 헤더 파일, Javascript : 번 들러)로 연결되는 경우가 많습니다. 줄 바꿈 문자를 생략하면 불쾌한 버그가 발생할 수 있습니다 (한 소스의 마지막 줄이 다음 소스 파일의 첫 줄과 연결됨). 바라건대 모든 소스 코드 연결 도구는 연결 된 파일 사이에 줄 바꿈을 삽입하지만 항상 그렇지는 않습니다.

문제의 핵심은 대부분의 언어에서 줄 바꿈이 의미 론적 의미를 가지며 파일 끝은 줄 바꿈 문자의 언어 정의 대안이 아닙니다. 따라서 마지막 문장을 포함하여 줄 바꿈 문자로 모든 문장 / 표현을 종료해야합니다.


1
C / C ++에서 당신은 한 줄에 전체 프로젝트를 작성할 수 있습니다. 줄 바꿈이 필요하지 않습니다.
놀라운 1

당신은 할 수 당신이 사용하지 않는 경우 ... 한 줄에 전체 프로젝트를 쓰기 //코드의 중간에 스타일의 코멘트를.
Doug Coburn

2

원본 파일에 줄 바꿈 문자가 없었을 것입니다.

그러나 리눅스에서 gedit 와 같은 일부 편집기 는 파일 끝에 줄 바꿈을 자동으로 추가합니다. 이런 종류의 편집기를 사용하는 동안이 메시지를 제거 할 수 없습니다.

이 문제를 극복하려고 시도한 것은 Visual Studio 코드 편집기로 파일을 여는 것입니다.

이 편집기는 마지막 줄을 명확하게 표시하며 원하는대로 줄을 삭제할 수 있습니다.


0

가치있는 일을 위해 Mac에서 IntelliJ 프로젝트를 만든 다음 프로젝트를 Windows 컴퓨터로 옮길 때이 문제가 발생했습니다. 모든 파일을 수동으로 열고 IntelliJ 창의 오른쪽 하단에서 인코딩 설정을 변경해야했습니다. 아마도이 질문을 읽은 사람이 저에게 몇 시간의 노동력을 절약 할 수 있다면 아마도 대부분 일어나지 않을 것입니다 ...

당사 사이트를 사용함과 동시에 당사의 쿠키 정책개인정보 보호정책을 읽고 이해하였음을 인정하는 것으로 간주합니다.
Licensed under cc by-sa 3.0 with attribution required.