Computer >> บทช่วยสอนคอมพิวเตอร์ >  >> การเขียนโปรแกรม >> Python

Absolute และ Relative Imports ใน Python


หลายครั้งเมื่อเราสร้างโค้ด Python เราพบว่าต้องเข้าถึงโค้ดจากไฟล์หรือแพ็กเกจ Python อื่น นี่คือเวลาที่คุณต้อง import ไฟล์หรือแพ็กเกจ Python อื่นเข้าไปในโค้ดปัจจุบัน วิธีตรงไปตรงมาคือเขียนคำสั่งด้านล่างที่ด้านบนของโปรแกรม Python ปัจจุบันของคุณ

import package_name or module_name
or
from package_name import module_name/object_name

เมื่อคำสั่งข้างต้นถูก parse interpreter จะทำดังนี้

  • Interpreter จะค้นหาชื่อในแคชของโมดูลทั้งหมดที่ถูก import ไปก่อนหน้านี้ ชื่อของแคชโมดูลนี้คือ sys.modules

  • หากไม่พบในขั้นตอนข้างต้น interpreter จะค้นหาในรายการโมดูลในตัว (built-in modules) โมดูลเหล่านี้เป็นส่วนหนึ่งของ Python standard libraries

  • ในกรณียังไม่พบในขั้นตอนที่ 2 interpreter จะค้นหาชื่อแพ็กเกจหรือโมดูลในรายการไดเรกทอรีที่กำหนดใน sys.path ซึ่งมีไดเรกทอรีปัจจุบันเป็นไดเรกทอรีแรกที่ค้นหา

  • เมื่อพบโมดูลที่ import ในขั้นตอนใดขั้นตอนหนึ่งข้างต้น ชื่อของแพ็กเกจหรือโมดูลจะถูกผูกกับขอบเขตท้องถิ่น (local scope) ของโปรแกรมปัจจุบัน

  • หากไม่พบแพ็กเกจหรือโมดูลเลย จะโยน ModuleNotFoundError

กฎเกี่ยวกับการ import

คำสั่ง import ควรระบุที่ด้านบนของไฟล์ที่ใช้คำสั่งเหล่านั้น ลำดับที่ import ต้องระบุมีดังนี้

  • โมดูลของ Python standard library

  • Import จาก third-party modules

  • Import จาก local applications

Absolute Import

ในประเภท import นี้ เราระบุพาธเต็มของแพ็กเกจ/โมดูล/ฟังก์ชันที่จะ import ใช้ dot (.) แทน slash (/) สำหรับโครงสร้างไดเรกทอรี

พิจารณาโครงสร้างไดเรกทอรีสำหรับแพ็กเกจดังนี้

python_project_name/packageA/moduleA1.py
python_project_name/packageA/moduleA2.py

สมมติ moduleA2 มีฟังก์ชันชื่อ myfunc เมื่อเราต้องการ import ฟังก์ชันนั้นไปยังโปรแกรม Python ปัจจุบัน โดยใช้ absolute path เราเขียนคำสั่ง import ดังนี้

from packageA.moduleA2 import myfunc

ข้อดีใหญ่ของ absolute import คือ ชี้ชัดว่าการ import เกิดขึ้นที่ไหน ส่วนข้อเสียคืออาจยาวมาก

Relative Import

ใน relative import เราระบุพาธของแพ็กเกจที่ import เป็น relative ตามตำแหน่งของสคริปต์ปัจจุบันที่ใช้โมดูลที่ import

Dot หนึ่งหมายถึงไดเรกทอรีขึ้นไปหนึ่งระดับจากตำแหน่งปัจจุบัน สองดอทหมายถึงขึ้นไปสองระดับ และไปเรื่อยๆ

พิจารณาโครงสร้างไดเรกทอรีสำหรับแพ็กเกจดังนี้

python_project_name/packageA/moduleA1.py
python_project_name/packageB/moduleB1.py

สมมติ moduleB1 ในโครงสร้างแพ็กเกจข้างต้นต้องการ import moduleA1 คำสั่ง import คือ:

from ..packageA import moduleA1

สองดอทบ่งบอกว่าจากตำแหน่งของ moduleB1 เราต้องย้ายไปไดเรกทอรี python_project_name แล้วไปที่ packageA เพื่อหา moduleA1

ประเภท import นี้สั้นและโปรเจกต์ระดับบนสุดสามารถย้ายจากตำแหน่งหนึ่งไปอีกตำแหน่งได้โดยไม่ต้องเปลี่ยนพาธในคำสั่ง import ได้ง่าย ข้อเสียคือถ้าโฟลเดอร์ import ถูกแชร์ โค้ดจะได้รับผลกระทบง่ายเมื่อมีการเปลี่ยนแปลงในพาธ