[파이썬] 파일 다루기(유니코드, 파일 읽기 등)

2018. 10. 21. 16:22개발/파이썬

기본적인 파일 읽고 쓰기 

대부분의 언어와 동일하게 open/close 함수를 이용해서 파일을 읽고 닫을 수 있습니다 .

f = open(path, "r")
f.close()

 

파일 인코딩 예외처리

텍스트 파일의 인코딩은 ANSI/유니코드/UTF-8 등 다양하게 존재 합니다. (노트패드에 파일 저장을 눌러보면 인코딩 선택 기능으로 확인 가능)  

파일의 인코딩을 정확히 알 경우에는 해당 인코딩으로 읽어 주면 되지만 해당 파일의 인코딩을 모를경우에는 일단 읽어보고 오류 나면 다시 읽는 식으로 처리해 줘야 합니다.(try ~ exception 활용)

import codecs  # file encoding
 
def readFile(self, path):
 
    ftype = 'normal'
    f = open(path, "r")
    lines = None
    try:
        lines = f.readlines()
    except:
        f.close()
        try:
            ftype = 'utf-8'
            f = codecs.open(path, "r", 'utf-8')
            lines = f.readlines()
        except:
            try:
                ftype = 'utf-16'
                f = codecs.open(path, "r", 'utf-16')
                lines = f.readlines()
            except:
                print('file 읽기 실패', path)
                return (False, ftype)
 
    f.close()
 
    for line in lines:
        
        sline = line.strip()
 
        # do something
        # print(findText)
 
    return (True, ftype)

 

파일의 텍스트를 한번에 읽어 리스트에 넣어 주는 함수 readlines()

파일 i/o 는 한번에 하는게 좋습니다 

readlines() 함수를 이용하면 파일 전체의 내용을 읽어 텍스트 리스트로 만들어 줍니다.

lines = f.readlines()
for line in lines:
   # do something

 

 

특정 폴더의 특정 확장자를 가진 파일을 모두 읽어 처리하기

폴더는 기본적으로 서브 폴더와 파일로 존재 합니다  서버 폴더는 다시 서브 폴더와 파일로 구성되어 있어, 재귀적 함수를 이용해서 폴더가 안 나올 때까지 계속 들여다 보면 됩니다   

import codecs  # file encoding
import os
 
class CFolderFile:
    def __init__(self):
        self.ftypelist  = {}
 
    def FolderNaviagte(self, path, extlst):
        for fname in os.listdir(path):
            fullname = os.path.join(path, fname)
 
            if os.path.isdir(fullname):
                self.FolderNaviagte(fullname, extlst)
            else:
                llist = fullname.split('.')
                ext = llist[-1]
                ext.lower()
 
                if ext in extlst :
                    ret, ftype =  self.readFile(fullname)
                    if not ftype in self.ftypelist:
                        self.ftypelist[ftype] = 1
                    else:
                        self.ftypelist[ftype] = self.ftypelist[ftype] + 1
 
        return True
 
    def readFile(self, path) :
        ftype = 'normal'
        f = open(path, "r")
        lines = None
        try:
            lines = f.readlines()
        except:
            f.close()
            try:
                ftype = 'utf-8'
                f = codecs.open(path, "r", 'utf-8')
                lines = f.readlines()
            except:
                try:
                    ftype = 'utf-16'
                    f = codecs.open(path, "r", 'utf-16')
                    lines = f.readlines()
                except:
                    print('file 읽기 실패', path)
                    return (False, ftype)
 
        f.close()
 
        for line in lines:
            sline = line.strip()
            # do something
 
        return (True, ftype)

 

위 클래스는 아래와 같이 호출하면 됩니다  예시는 d:\test 폴더 밑에 있는 모든 cpp, txt 확장자 파일을 읽도록 하는 예입니다.

objFolder = CFolderFile()
Path = 'D:\\test'
extlist = {'cpp', 'txt'}
objFolder.FolderNaviagte(Path, extlist)