티스토리 뷰

반응형

Stack Overflow에 자주 검색, 등록되는 문제들과 제가 개발 중 찾아 본 문제들 중에서 나중에도 찾아 볼 것 같은 문제들을 정리하고 있습니다.

Stack Overflow에서 가장 먼저 확인하게 되는 가장 높은 점수를 받은 Solution과 현 시점에 도움이 될 수 있는 가장 최근에 업데이트(최소 점수 확보)된 Solution을 각각 정리하였습니다.

 

아래 word cloud를 통해 이번 포스팅의 주요 키워드를 미리 확인하세요.

Search and replace a line in a file in Python

Python에서 파일의 줄 검색 및 바꾸기

 문제 내용 

I want to loop over the contents of a text file and do a search and replace on some lines and write the result back to the file. I could first load the whole file in memory and then write it back, but that probably is not the best way to do it.

텍스트 파일의 내용을 루프하여 검색하고 일부 줄을 바꾸고 결과를 파일에 다시 쓰고 싶습니다. 먼저 전체 파일을 메모리에 로드한 다음 다시 쓸 수는 있지만, 그렇게 하는 것이 최선의 방법은 아닐 것 같습니다.

 

What is the best way to do this, within the following code?

다음 코드 내에서 이를 수행하는 가장 좋은 방법은 무엇입니까?
f = open(file)
for line in f:
    if line.contains('foo'):
        newline = line.replace('foo', 'bar')
        # how to write this newline back to the file

 

 

 높은 점수를 받은 Solution 

The shortest way would probably be to use the fileinput module. For example, the following adds line numbers to a file, in-place:

가장 짧은 방법은 파일 입력 모듈을 사용하는 것입니다. 예를 들어, 다음은 파일에 행 번호를 인플레이스로 추가합니다.
import fileinput

for line in fileinput.input("test.txt", inplace=True):
    print('{} {}'.format(fileinput.filelineno(), line), end='') # for Python 3
    # print "%d: %s" % (fileinput.filelineno(), line), # for Python 2

 

What happens here is:

여기서 일어나는 일은 다음과 같습니다.

 

  1. The original file is moved to a backup file
  2. The standard output is redirected to the original file within the loop
  3. Thus any print statements write back into the original file
1. 원본 파일이 백업 파일로 이동됩니다.
2. 표준 출력이 루프 내의 원본 파일로 리디렉션됩니다.
3. 따라서 모든 인쇄문은 원본 파일에 다시 기록됩니다.

 

fileinput has more bells and whistles. For example, it can be used to automatically operate on all files in sys.args[1:], without your having to iterate over them explicitly. Starting with Python 3.2 it also provides a convenient context manager for use in a with statement.

파일 입력에는 매력적인 기능이 있습니다. 예를 들어 sys.args[1:1]의 모든 파일에 대해 명시적으로 반복할 필요 없이 자동으로 작동하는 데 사용할 수 있습니다. 파이썬 3.2부터는 with 문에 사용할 수 있는 편리한 컨텍스트 관리자를 제공합니다.

 


While fileinput is great for throwaway scripts, I would be wary of using it in real code because admittedly it's not very readable or familiar. In real (production) code it's worthwhile to spend just a few more lines of code to make the process explicit and thus make the code readable.

파일 입력은 일회용 스크립트에 매우 유용하지만, 읽기 쉬우거나 친숙하지 않기 때문에 실제 코드에서 사용하는 것을 조심할 것입니다. 실제 (생산) 코드에서는 프로세스를 명시적으로 만들어 코드를 읽을 수 있도록 하기 위해 코드의 몇 줄만 더 쓰는 것이 가치가 있습니다.

 

There are two options:

두 가지 옵션이 있습니다.

 

  1. The file is not overly large, and you can just read it wholly to memory. Then close the file, reopen it in writing mode and write the modified contents back.
  2. The file is too large to be stored in memory; you can move it over to a temporary file and open that, reading it line by line, writing back into the original file. Note that this requires twice the storage.
1. 그 파일은 너무 크지 않고, 당신은 그것을 완전히 메모리로 읽을 수 있습니다. 그런 다음 파일을 닫고 쓰기 모드에서 다시 열고 수정된 내용을 다시 씁니다.
2. 파일이 너무 커서 메모리에 저장할 수 없습니다; 임시 파일로 파일을 이동하여 열어서 한 줄씩 읽고 원본 파일에 다시 쓸 수 있습니다. 이를 위해서는 스토리지가 두 배로 필요합니다.

 

 

 

 가장 최근 달린 Solution 

fileinput is quite straightforward as mentioned on previous answers:

이전 답변에서 언급한 바와 같이 파일 입력은 매우 간단합니다.
import fileinput

def replace_in_file(file_path, search_text, new_text):
    with fileinput.input(file_path, inplace=True) as file:
        for line in file:
            new_line = line.replace(search_text, new_text)
            print(new_line, end='')

 

Explanation:

설명:

 

  • fileinput can accept multiple files, but I prefer to close each single file as soon as it is being processed. So placed single file_path in with statement.
  • print statement does not print anything when inplace=True, because STDOUT is being forwarded to the original file.
  • end='' in print statement is to eliminate intermediate blank new lines.
1. fileinput은 여러 파일을 허용할 수 있지만 각 단일 파일이 처리되는 즉시 닫는 것을 선호합니다. 따라서 with 문에 단일 file_path를 배치했습니다.
2. STDOUT이 원래 파일로 전달되기 때문에 print 문은 inplace=True일 때 아무 것도 인쇄하지 않습니다.
3. print 문에서 end=' '는 중간 빈 새 줄을 제거하는 것입니다.

 

You can used it as follows:

다음과 같이 사용할 수 있습니다.
file_path = '/path/to/my/file'
replace_in_file(file_path, 'old-text', 'new-text')

 

 

출처 : https://stackoverflow.com/questions/39086/search-and-replace-a-line-in-a-file-in-python

반응형
댓글
공지사항
최근에 올라온 글