1. 子產品
- 一個子產品就是一個包含python代碼的檔案,字尾名稱是.py就可以,子產品就是個python檔案
- 為什麼我們用子產品
- 程式太大,編寫維護非常不友善,需要拆分
- 子產品可以增加代碼重複利用的方法
- 當作命名空間使用,避免命名沖突
- 如何定義子產品
- 子產品就是一個普通檔案,是以任何代碼可以直接書寫
- 不過根據子產品的規範,最好在本塊中編寫以下内容
- 函數(單一功能) - 類(相似功能的組合,或者類似業務子產品) - 測試代碼
- 如何使用子產品
- 子產品直接導入
- 子產品名稱直接以數字開頭,需要借助importlib幫助
- 文法
import module_name module_name.function_name module_name.class_name
- 案例 01.py,02.py,p01.py,p02.py
# 案例 01.py # 包含一個學生類 # 一個sayHello函數 # 一個列印語句 class Student(): def __init__(self, name = "NoName", age = 18): self.name = name self.age = age def say(self): print("My name is {0}".format(self.name)) def sayHello(): print("Hi, ") print("我是子產品p0")
# 案例 02.py # 借助于importlib包可以實作導入以數字開頭的子產品名稱 import importlib # 相當于導入了一個叫01的子產品并把導入子產品指派給了a a = importlib.import_module("01") stu = a.Student() stu.say()
# 案例 p01.py # 包含一個學生類 # 一個sayHello函數 # 一個列印語句 class Student(): def __init__(self, name = "NoName", age = 18): self.name = name self.age = age def say(self): print("My name is {0}".format(self.name)) def sayHello(): print("Hi, ") # 此判斷語句建議一直作為程式的入口 if __name__ == '__main__': print("我是子產品p01")
# 案例 p02.py import p01 stu = p01.Student("xiaojing", 19) stu.say() p01.sayHello()
My name is xiaojing Hi,
- import 子產品 as 别名
- 導入的同時給子產品起一個别名 - 其餘用法跟第一種相同 - 案例 p03.py
# 案例 p03.py import p01 as p stu = p.Student("yueyue", 18) stu.say()
My name is yueyue
- from module_name import func_name, class_name
- 按上述方法有選擇性的導入 - 使用的時候可以直接使用導入的内容,不需要字首 - 案例 p04
# 案例 p04.py from p01 import Student, sayHello stu = Student() stu.say() sayHello()
My name is NoName Hi,
- from module_name import *
- 導入子產品所有内容 - 案例 p05.py
# 案例 p05.py from p01 import * sayHello() stu = Student("yaona", 20) stu.say()
Hi, My name is yaona
- 子產品直接導入
-
`__main__` 的使用if __name__ ==
- 可以有效的避免子產品代碼被導入的時候被動執行的問題
- 建議所有程式的入口都以此代碼為入口
2. 子產品的搜尋路徑和存儲
- 什麼是子產品的搜尋路徑
- 加載子產品的時候,系統會在哪些地方尋找此子產品
- 系統預設的子產品搜尋路徑
import sys sys.path 屬性可以擷取路徑清單 # 案例 p06.py
# 案例 p06.py import sys print(type(sys.path)) print(sys.path) for p in sys.path: print(p)
<class 'list'> ['D:\\python\\project\\包管理', 'D:\\PyCharm Community Edition 2019.1.1\\helpers\\pydev', 'D:\\python\\project', 'D:\\PyCharm Community Edition 2019.1.1\\helpers\\third_party\\thriftpy', 'D:\\PyCharm Community Edition 2019.1.1\\helpers\\pydev', 'C:\\Users\\user\\.PyCharmCE2019.1\\system\\cythonExtensions', 'D:\\python\\project\\包管理', 'D:\\Anaconda3\\envs\\opp\\python37.zip', 'D:\\Anaconda3\\envs\\opp\\DLLs', 'D:\\Anaconda3\\envs\\opp\\lib', 'D:\\Anaconda3\\envs\\opp', 'D:\\Anaconda3\\envs\\opp\\lib\\site-packages'] D:\python\project\包管理 D:\PyCharm Community Edition 2019.1.1\helpers\pydev D:\python\project D:\PyCharm Community Edition 2019.1.1\helpers\third_party\thriftpy D:\PyCharm Community Edition 2019.1.1\helpers\pydev C:\Users\user\.PyCharmCE2019.1\system\cythonExtensions D:\python\project\包管理 D:\Anaconda3\envs\opp\python37.zip D:\Anaconda3\envs\opp\DLLs D:\Anaconda3\envs\opp\lib D:\Anaconda3\envs\opp D:\Anaconda3\envs\opp\lib\site-packages
- 添加搜尋路徑
sys.path.append(dir)
- 子產品的加載順序
- 搜尋記憶體中已經加載好的子產品
- 搜尋python的内置子產品
- 搜尋sys.path路徑
包
- 包是一種組織管理代碼的方式,包裡面存放的是子產品
- 用于将子產品包含在一起的檔案夾就是包
- 自定義包的結構
|---包
|---|--- __init__.py 包的标志檔案
|---|--- 子產品1
|---|--- 子產品2
|---|--- 子包(子檔案夾)
|---|---|--- __init__.py
|---|---|--- 子包子產品1
|---|---|--- 子包子產品2
- 包的導入操作
- import package_name
- 直接導入一個包,可以使用__init__.py中的内容
-
使用方式是:
package_name.func_name
package_name.class_name.func_name()
- 此種方式的通路内容是
- 案例 pkg01, p07.py
# pkg01.__init__py def inInit(): print("I am in init of package") # pkg01.p01.py class Student(): def __init__(self, name = "NoName", age = 18): self.name = name self.age = age def say(self): print("My name is {0}".format(self.name)) def sayHello(): print("Hi, ") print("我是子產品p01")
# 案例 p07.py import pkg01 pkg01.inInit()
I am in init of package
- import package_name as p
- 具體用法跟作用方式,跟上述簡單導入一緻
- 注意的是此種方法是預設對__init__.py内容的導入
- import package.module
- 導入包中某一個具體的子產品
- 使用方法
package.module.func_name package.module.class.fun() package.module.class.var
- 案例 p08.py
# 案例 p08.py import pkg01.p01 stu = pkg01.p01.Student() stu.say()
我是子產品p01 My name is NoName
- import package.module as pm
- import package_name
- from ... import 導入
- from package import module1, module2, module3, ... ...
- 此種導入方法不執行
的内容__init__
from pkg01 import p01 p01.sayHello()
- from package import *
- 導入目前包
檔案中所有的函數和類__init__.py
-
func_name()
class_name.func_name()
class_name.var
- 案例 p09.py, 注意此種導入的具體内容
- 導入目前包
# 案例 p09.py from pkg01 import * inInit() stu = Student()
I am in init of package NameError: name 'Student' is not defined
- from package.module import *
- 導入包中指定的子產品的所有内容
- 在開發環境中經常會引用其他子產品,可以在目前包中直接導入其他子產品中的内容
- import 完整的包或者子產品的路徑
-
的用法__all__
- 在使用from package import 的時候, 可以導入的内容
-
中如果檔案為空,或者沒有__init__.py
, 那麼隻可以把__all__
中的内容導入__init__
-
如果設定了__init__
的值,那麼則按照__all__
指定的子包或者子產品進行加載__all__
中的内容__init__
-
__all__=['module1', 'module2', 'package1'... ...]
- 案例 pkg02,p10.py
# pkg02.__init__.py __all__=['p01'] def inInit(): print("T am in init of package") # pkg02.p01.py class Student(): def __init__(self, name = "NoName", age = 18): self.name = name self.age = age def say(self): print("My name is {0}".format(self.name)) def sayHello(): print("Hi, ") # 此判斷語句建議一直作為程式的入口 if __name__ == '__main__': print("我是子產品p01")
# 案例 p10.py from pkg02 import * stu = p01.Student() stu.say()
My name is NoName
命名空間
- 用于區分不同位置不同功能但相同名稱的函數或者變量的一個特定字首
-
作用是防止命名沖突
setName()
Student.setName()
Dog.setName()