본문 바로가기
목차
Python

[Python] file: open and close

by ds31x 2023. 7. 4.
728x90
반응형

Python 에서 file을 처리하기 위해선 다른 프로그래밍 언어와 마찬가지로 file에 대한 접근이 가능한 object를 얻어와야함.

  • 이같은 object는 file object, file handler, file descriptor 등의 여러 이름으로 불리며,
    • Python의 경우로 한정하면 File Object가 더 많이 사용됨.
    • file descriptor는 OS에서 열려진 file에 대해 할당하는 일종의 int형 id임.
  • 이를 얻어오는 작업을 가르켜 open이라고 지칭하는게 일반적임.
  • 때문에 file을 처리하기 위해 가장 먼저 수행되는 작업을 file을 연다(open) 라고 표현함.
  • file에 대한 작업이 완료되고 나면, file object를 통한 close를 수행한다.


file open과 file close - Stream 생성 및 해제.

Python에서 파일을 open한다는 것은

  • OS로 하여금 해당 file에 대한 입출력 스트림(stream)을 생성하도록 요청하는 행위임.
  • 이 요청은 open() 함수를 통해 수행되며, 그 결과로 파일 객체(file object)를 얻게 됨.
  • file object는 스트림(stream) 인터페이스를 제공.
  • 즉, file의 content(내용)을 순차적으로 읽거나 쓸 수 있도록 버퍼링된 데이터 흐름을 관리.

따라서 file을 닫는다(close)는 것은:

  • stream에 남아 있는 데이터를 모두 디스크에 기록하고(flush),
  • 관련된 buffer와 descriptor 등 OS 의 resource를 해제하는 것을 의미 (OS에게 반환).
  • C 에서는 close를 개발자가 명시적으로 반드시 해줘야하는 반면,
  • Python 에서는 context manager with를 통해 이를 쉽게 처리할 수 있다는 장점을 가짐.

2024.09.11 - [CE] - [CE] Stream이란

 

[CE] Stream이란

Stream:데이터를 연속적으로 흐르는 방식으로 처리한다는 개념으로,데이터의 입출력을 일종의 bit (or byte) 들의 흐름으로 여겨서 처리하는 것으로 생각하고이와 같은 방식으로 I/O가 이루어지는 대

ds31x.tistory.com

 

Python에서
open을 통해 얻은 file object를 명시적으로 닫지 않더라도
더이상 참조되지 않는 경우엔 자동으로 close가 이뤄짐.
예를 들어
함수 내부에서 open된 경우
해당 함수가 반환된 이후에는 자동으로 close가 된다.
하지만 가급적 명시적으로 close를 하는 것이 좋고,
권장되는 것은
context manager를 이용하여 파일을 처리
하는 것이다.


File 열기 : open

fin = open('file_path', 'wt')
  • file_path :
    • open하려고 하는 파일의 path - absoulte path 또는 relative path.
    • 이는 문자열 argument로 지정해줌.
  • wt :
    • mode라고 불리며,
    • file을 어떤 작업이 가능하도록 열지를 지정하는 문자열임.

참고로 반환되는 객체는 io.IOBase 의 subclass 임.

object
 └── io.IOBase
      ├── io.RawIOBase
      │     └── io.FileIO
      ├── io.BufferedIOBase
      │     ├── io.BufferedReader
      │     ├── io.BufferedWriter
      │     └── io.BufferedRandom
      └── io.TextIOBase
            └── io.TextIOWrapper

위와 같은 Hierarchy에서 실제 사용되는 클래스를 mode 별로 정리하면 다음과 같음:

  • `w`,`r`,`a` (text 모드): io.TextIOWrapper (내부적으로 BufferedIOBase 기반 객체를 감싸고 있음)
  • `wb` : io.BufferedWriter
  • `rb` : io.BufferedReader
  • `ab` : io.BufferedRandom
  • buffer size 를 0으로 할당시, io.FileIO (물론 binary mode임)

path (경로)

Python은 다른 프로그래밍 언어와 마찬가지로 기본적으로 current working directory (cwd, 또는 present working directory라고도 불림)를 기준으로 하는 relative path로 파일 경로를 지정가능함.

  • cwd :
    • python interpreter로 프로그램을 수행하는 경우,
    • 해당 수행을 시키기 위해 python command가 입력될 당시 위치하고 있던 directory를 가르킴.

하지만 가급적 absolute path를 사용하는 것이 에러를 줄이는 방법 중 하나임.

 

 

Path 및 Python에서 cwd등의 처리방법에 대한 자세한 내용은 다음 URL을 참고할 것.

https://dsaint31.tistory.com/222

 

Path (경로)

파일 시스템 내에서 특정 파일(혹은 디렉토리)의 위치를 나타내는 문자열Absolute Path (절대 경로)현 작업디렉토리(cwd)와 관계없이 절대적 위치드라이브:\폴더\폴더\파일명 (Windows)c:\Windows\System32\dri

dsaint31.tistory.com


mode argument

mode는 하나 또는 두개의 character로 이루어짐.

첫번째 character는 열고자 하는 file에 대해 어떤 작업을 가능하게할지를 지정함.

  • r :
    • read 즉 읽기모드로 기존에 존재하던 파일을 연다
    • 없을 경우 FileNotFoundError 발생.
  • w :
    • write 즉 쓰기모드로 파일을 연다.
    • 기본 파일이 있을 경우, 기존 파일의 모든 내용이 삭제되고 새로 쓰여짐.
  • a :
    • append 즉 뒤에 추가하는 모드로 기존 파일을 연다.
    • 파일이 없는 경우, 해당 주어진 path로 새로 생성됨.
  • x :
    • write 모드이나 반드시 새로 만드는 파일이어야 한다.
    • 기존 파일이 존재시 FileExistException 발생.

두번째 character는 열고자 하는 file의 종류를 지정한다.

  • t :
    • 기본값으로 file을 text파일 이라고 생각하고 open.
    • 때문에 t는 생략가능함.
  • b :
    • file을 binary 파일이라고 생각하고 open.
    • 기본적으로 text file로 열게 되어있기 때문에 반드시 binary file을 열 때는 b를 추가해줘야함.

file 닫기

fin = open('file_path', 'wt')

# fin에 내용을 쓰는 처리 등등.

fin.close() # file 닫기

 

파일을 닫지 않으면 발생할 수 있는 문제는 다음과 같음.

  • buffer 에 남은 데이터가 디스크에 기록되지 않을 수 있음 (특히 write()flush 미수행 시).
  • OS에서 할당된 file descriptor 가 반환되지 않아 file descriptor의 누수 발생.
  • OS는 제한된 개수 이상의 파일을 동시에 열 수 없는데, 이같은 누수가 계속되면 열 수 있는 파일의 수가 계속 줄어들어 결국 Too many open files 오류가 일어나게 됨(파일을 열지 못하게 되는 상태에 이름).

 


Context manager : with statement

context manager는 원하는 특정 구간에서 resource를 얻고 반환하는 것을 관리해준다.

 

context manager 는 with statement와 함께 사용되어

  • with statment로 시작하는 code block으로 들어갈 경우
    • 정해진 resource를 얻는 처리(__enter__)가 자동으로 수행되며,
  • 해당 block을 나갈 때
    • 자동으로 해당 resource를 반환하는 처리(__exit__)가 수행된다.

 

구문은 다음과 같음.

# 다음 with 문의 expression_for_resource 는 expression으로 evaluation이 이루어짐.
# 해당 evaluaiton으로 얻어진 리소스 관련 object가 가지고 있는 __enter__ 메서드가 호출됨.
# - __enter__ 메서드에서 해당 object를 사용하기 위한 초기 작업이 구현되어 있음.
#
# as 를 통해 해당 object를 참조하는 variable name 이 설정됨.
# 이후 context manager 가 관리하는 block이 수행.
# 해당 block을 나갈 때, with로 얻어진 object의 __exit__ 메서드가 호출됨.
# - __exit__ 메서드에서 해당 object와 관련된 resource를 반환하는 작업(file의 경우 close)들이 구현됨.
#
with expression_for_resource as alias_name: 
    # alias_name이 참조하는 resource 객체를 다루는 작업이 이루어짐.
    # 이 block내에서 나가면 resource 관련 객체를 반환이 이루어짐.

 

간단하게 파일을 with statement로 처리하면 다음과 같음.

with open('file_path', 'wt') as fin:
    fin.write('test!')

 

fin.close()가 명시적으로 호출되지 않았지만 위의 코드는 아래 코드와 동치임.

fin = open('file_path', 'wt')
fin.write('test!') 
fin.close()

 

Context Manager에 대한 보다 자세한 것은 다음 URL을 참고.

2024.11.27 - [Python] - [Py] Context Manager: with statement!

 

[Py] Context Manager: with statement!

1. Python의 Context Manager 개념Python의 Context Manager는 resource(자원, 리소스)를 안전하게 관리하기 위한 도구(특정 메서드를 구현한 객체임). 일반적으로 file(파일), socket(네트워크 소켓), connection(데이

ds31x.tistory.com


관련된 글들

2023.12.05 - [Python] - [Python] File Handling

 

[Python] File Handling

File 열고 닫기. 2023.07.04 - [Python] - [Python] file : open and close [Python] file : open and close Python 에서 file을 처리하기 위해선 다른 프로그래밍 언어와 마찬가지로 file에 대한 접근이 가능한 object를 얻어와

ds31x.tistory.com


 

728x90