본문 바로가기
Python

[작고귀여운팁] 변수로 사용할 수 없는 이름의 파이썬 파일 임포트하기

by 돈민찌 2021. 9. 22.
반응형

파이썬의 변수/함수의 명명 규칙은 다른 프로그래밍 언어와 비슷하다.

  • 영문 문자와 숫자를 사용할 수 있다.
  • 대소문자를 구분한다. (일반적으로 snake_case를 사용한다.)
  • 문자부터 시작해야 하며 숫자부터 시작하면 안된다.
  • _(밑줄 문자)로 시작할 수 있다.
  • 특수 문자(+, -, *, /, $, @, &, %등)는 사용할 수 없다.
  • 파이썬의 키워드(if, for, while, and, or 등)는 사용할 수 없다. => 예약어

# 참고로 예약어는 내장 모듈인 keyword 모듈의 kwlist를 프린트해서 확인해 볼 수 있다.

['False', 'None', 'True', 'and', 'as', 'assert', 'async', 'await', 'break', 'class', 'continue', 'def', 'del', 'elif', 'else', 'except', 'finally', 'for', 'from', 'global', 'if', 'import', 'in', 'is', 'lambda', 'nonlocal', 'not', 'or', 'pass', 'raise', 'return', 'try', 'while', 'with', 'yield']

그런데 개발자가 파이썬 파일의 이름으로 이러한 규칙들을 매번 신경쓰고 지키기 싫을 수도 있다. 

이번에 강의 내용 챕터에 따라 앞에 001,002... 로 시작하는 파일명을 사용했는데, 이렇게 작성된 파일도 모듈로 사용할 수 있을까?

from 009_hash_table_dict import LinkedDict

# 임포트된 모듈도 변수 명명 규칙에 따라 사용되기 때문에 이 임포트 구문은 동작하지 않는다.

하지만 또 해당 파일에서 가져오고자 하는 함수나 클래스 등을 복사해 가져오는 것은 번거롭기도 하고 실제로 파이참에서도 "중복된 코드가 ㅇㅇ파일에 있습니다."라는 주의 표시가 나타나서 신경이 쓰인다.

이럴 때 보통 사용하는 것이 __import__ 내장 메소드와, importlib이라는 내장 모듈의 import_module이다. __import__는 좀 더 로우한 메소드라 따로 임포트할 것도 없이 사용할 수 있는데 사용법이 약간 더 어렵기도 하고, 파이썬 자체에서도 importlib을 권장하는 것 같으니까 importlib을 사용하는 것을 알아보자

현재 가져오고자 하는 파일의 내용은 다음과 같다.

```009_hash_table_dict.py

class Node:
    def __init__(self, data):
        self.data = data
        self.next = None


class LinkedTuple:
    def __init__(self):
        self._items = list()

    def add(self, key, value):
        self._items.append((key, value))
        return

    def get(self, key):
        for k, value in self._items:
            if k == key:
                return value
        return "cannot get key-value"

    @property
    def items(self):
        return self._items


class LinkedDict:
    def __init__(self):
        self._items = list()
        for i in range(12):
            self._items.append(LinkedTuple())

    @property
    def items(self):
        return self._items

    def put(self, key, value):
        i = hash(key) % len(self._items)
        self._items[i].add(key, value)

    def get(self, key):
        i = hash(key) % len(self._items)
        return self._items[i].get(key)

이 파일을 같은 디렉토리 내의 010_quiz 파일에서 가져다 쓰고 싶다. 내부 구현을 위해 사용된 Node와 LinkedTuple이 아닌 LinkedDict만 사용할 생각이다. 이 경우 작성할 내용은 다음과 같다.

import importlib
hash_table = importlib.import_module('009_hash_table_dict')
LinkedDict = getattr(hash_table, 'LinkedDict')

if __name__ == '__main__':
    my_dict = LinkedDict()
    my_dict.put("hi", "hello")
    print(my_dict.get("hi"))
    my_dict.put("hey", "wassup")
    print(my_dict.get("hey"))

importlib 모듈의 import_module 메소드는 문자열로 입력받은 파일명의 파일이 존재하는지 확인하고, 있는 경우 그 모듈 자체를 반환한다. 그리고 getattr()이라는 내장 함수를 통해 모듈에서 LinkedDict라는 클래스를 가져다 쓰겠다고 선언한다. 그리고 반환된 값을 똑같이 사용하면 된다. 실제로 더 복잡하고 유용한 사용법이 있지만, 내가 사용해 본 부분은 이 부분 뿐이고 이것만 사용해도 모듈화할 수 있는 파일의 범위가 훨씬 넓어지기 때문에 충분한 것 같다.

더 궁금한 내용이 있다면 파이썬의 공식문서를 참고하자 그럼 안뇽

 

importlib — import의 구현 — Python 3.9.7 문서

importlib — import의 구현 소스 코드: Lib/importlib/__init__.py 소개 importlib 패키지의 목적은 두 가지입니다. 하나는 파이썬 소스 코드에서 import 문(그리고, 확장하면 __import__() 함수)의 구현을 제공하는

docs.python.org

 

 

내장 함수 — Python 3.9.7 문서

내장 함수 파이썬 인터프리터에는 항상 사용할 수 있는 많은 함수와 형이 내장되어 있습니다. 여기에서 알파벳 순으로 나열합니다. abs(x) 숫자의 절댓값을 돌려줍니다. 인자는 정수, 실수 또는 __

docs.python.org

 

반응형

댓글