Python之路(第十二篇)程序解耦、模块介绍\导入\安装、包
一、程序解耦
解耦总的一句话来说,减少依赖,抽象业务和逻辑,让各个功能实现独立。
直观理解“解耦”,就是我可以替换某个模块,对原来系统的功能不造成影响。是两个东西原来互相影响,现在让他们独立发展;核心思想还是最小职责,每个地方都只做一件事情;只要一个地方负责了多项事情,就存在解耦的可能。在系统每个层次都可以体现解耦的思想,比如在架构层面把存储和业务逻辑解耦,把动态页面和静态页面解耦;在模块层面把业务模块和统计模块解耦;在代码层面把多个功能解耦等等。
低耦合,高内聚---模块之间低耦合,模块内部高内聚。一个系统有多个模块组成,在划分模块时,要把功能关系紧密的放到一个模块中(高内聚),功能关系远的放到其它模块中。模块之间的联系越少越好,接口越简单越好(低耦合,细线通信)。
二、模块
概念
在计算机程序的开发过程中,随着程序代码越写越多,在一个文件里代码就会越来越长,越来越不容易维护。为了编写可维护的代码,我们把很多函数分组,分别放到不同的文件里,这样,每个文件包含的代码就相对较少,很多编程语言都采用这种组织代码的方式。在Python中,一个.py文件就称之为一个模块(Module)。
使用模块的好处
最大的好处是大大提高了代码的可维护性;其次,编写代码不必从零开始。当一个模块编写完毕,就可以被其他地方引用。
模块的种类
python标准库
第三方模块
应用程序自定义模块:自定义模块时要注意命名,不能和Python自带的模块名称冲突。
模块的导入方法
import
import module1
import 模块名,一般是导入python的内置模块
import as
import multiprocessing as mul
在之后的代码中就可以直接用mul.方法名了,不用写长长的multiprocessing.方法名
from…import 语句
from modname import name1[, name2[, ... nameN]]
from 模块 import 方法名 ,这个声明不会把整个modulename模块导入到当前的命名空间中,只会将它里面的name1或name2单个方法引入到执行文件里
from…import* 语句
from modname import *
这提供了一个简单的方法来导入一个模块中的所有项目。然而这种声明不该被过多地使用。大多数情况, Python程序员不使用这种方法,因为引入的其它来源的命名,很可能覆盖了已有的定义。
注意:
模块一旦被导入,即相当于执行了一个.py文件(导入模块所在的文件)里的代码
import的工作机制
import语句导入指定的模块时会执行3个步骤
1.找到模块文件:在模块搜索路径下搜索模块文件
程序的主目录
PYTHONPATH目录
标准链接库目录
2.编译成字节码:文件导入时会编译,因此,顶层文件的.pyc字节码文件在内部使用后会被丢弃,只有被导入的文件才会留下.pyc文件
3.执行模块的代码来创建其所定义的对象:模块文件中的所有语句从头至尾依次执行,而此步骤中任何对变量名的赋值运算,都会产生所得到的模块文件的属性(所以自定义函数不要和模块中的名称重合)
不同目录类型的模块文件导入
1、与执行文件同目录模块导入
文件目录结构如下
%E3%80%90day21%E3%80%91\%E4%B8%8E%E6%89%A7%E8%A1%8C%E6%96%87%E4%BB%B6%E5%90%8C%E7%9B%AE%E5%BD%95%E6%A8%A1%E5%9D%97%E5%AF%BC%E5%85%A5.png?lastModify=1525681785)

test.py是执行文件,想调用manage.py模块
可以直接用
import manage
或者
from manage import *
2、不同文件目录的模块导入
M2
├── bin
│ ├── __init__.py
│ └── start.py [程序入口]
├── conf
│ ├── __init__.py
│ └── settings.py
├── core
│ ├── __init__.py
│ ├── accounts.py
│ ├── db_handler.py
│ ├── logger.py
│ ├── main.py
│ └── transaction.py
├── test.py
start.py是执行文件,不同目录下面入口程序得目录加载到sys.path即环境变量中,就可以跨模块调用了
在settings.py 里加入
import sys,os
BASE_DIR = os.path.dirname(os.path.dirname(os.path.abspath(__file__)))
sys.path.append(BASE_DIR)
这里os.path.abspath(__file__)获取返回settings.py规范化的绝对路径(包含文件),
os.path.dirname(os.path.abspath(__file__))获取当前运行脚本的绝对路径(去掉最后一个文件),
os.path.dirname(os.path.dirname(os.path.abspath(__file__)))获取当前运行脚本的绝对路径(去掉最后一个路径)
注意的一点是:直接用路径添加sys.path.append()添加目录时注意是在windows还是在Linux下,windows下需要‘\’否则会出错。
此时的模块搜索的主目录是 */M2/,即在M2文件夹下搜索
需求1:
mian.py想要引用accounts模块下的函数需要
from core import accounts
也可以这样写
from . import accounts
从当前目录导入模块(但是这里添加的搜索主目录是上级目录,即这个例子的M2文件夹)
需求2:
main.py 想要引用settings模块需要
from conf import settings
需求3:
test.py想要引用logger.py模块需要
from core import logger
from ..proj import hello (待补充)
注意:python使用. .. 相对导入模块要满足两个条件:
1.文件夹中必须有__init__.py文件,该文件可以为空,但必须要有
2.不能作为顶层模块来执行该文件夹中得py文件(即不能作为主函数得入口) 意思:..后不能到主函数入口得目录下
多层目录的模块导入
例子
index.py位置为D:\test_package\a\b\c\index.py
文件目录树
D:.
│ test.py
│ __init__.py
│
├─a
│ │ __init__.py
│ │
│ ├─b
│ │ └─c
│ │ index.py
│ │ __init__.py
│ │
│ └─__pycache__
│ __init__.cpython-36.pyc
│
└─__pycache__

test.py想要导入index模块需要
from a.b.c import index
内置变量: __file__表示当前的文件名
os.path.abspath(path) :返回path的绝对路径
os.path.dirname(path) :返回path的目录(去掉最后一级目录或文件)
例子
index.py文件位置为D:\python\exercise\test_package\b\index.py
在index.py写入
import os
BASE_DIR0 =os.path.abspath(__file__)
BASE_DIR1 = os.path.dirname(os.path.abspath(__file__)) #去掉最后一个文件,返回路径
BASE_DIR2 = os.path.dirname(os.path.dirname(os.path.abspath(__file__)))#去掉最后一级目录返回路径
print(BASE_DIR0)
print(BASE_DIR1)
print(BASE_DIR2)
print("这里是index")
运行输出结果
D:\python\exercise\test_package\b\index.py
D:\python\exercise\test_package\b
D:\python\exercise\test_package
这里是index
if __name__ == '__main__':
一个模块文件可以直接执行或被导入
每个模块都有一个名为__name__的内置变量,此变量值会根据调用此模块的方式发生变化:\1. 如果此文件被作为模块导入,则__name__的值为模块名称\2. 如果此文件被直接执行,则__name__的值为“__main__”
我们在创建模块时,在尾部添加如下代码进行模块的自我测试if __name__ == '__main__':
...
如果模块被导入,则 if 后的语句就不会执行
安装第三方模块
安装第三方模块有两种方式:
1.通过包管理工具pip完成的
即pip install 模块名或者pip3 install 模块名
注意:Mac或Linux上有可能并存Python 3.x和Python 2.x,因此对应的pip命令是pip3
2.下载源码=> 解压源码=> 进入目录
源码格式大概都是 zip 、 tar.zip、 tar.bz2格式的压缩包。解压这些包,进入解压好的文件夹,通常会看见一个 setup.py 的文件。打开命令行,进入该文件夹。
python setup.py install
三、包
包一个文件夹下有多个.py文件,加上__init__空文件,这个文件夹就是一个包了
包是一个有层次的文件目录结构,它定义了一个由模块和子包组成的Python应用执行环境
基于包,Python在执行模块导入时可以指定模块的导入路径 import pack1.pack2.mod1
每个包内都必须有__init__.py文件,可包含python代码,但通常为空,仅用于扮演包初始化、替目录产生模块命名空间以及使用目录导入时实现from*行为的角色
Python之路(第十二篇)程序解耦、模块介绍\导入\安装、包的更多相关文章
- Python之路(第二十二篇) 面向对象初级:概念、类属性
一.面向对象概念 1. "面向对象(OOP)"是什么? 简单点说,“面向对象”是一种编程范式,而编程范式是按照不同的编程特点总结出来的编程方式.俗话说,条条大路通罗马,也就说我们使 ...
- Python开发【第二十二篇】:Web框架之Django【进阶】
Python开发[第二十二篇]:Web框架之Django[进阶] 猛击这里:http://www.cnblogs.com/wupeiqi/articles/5246483.html 博客园 首页 ...
- Python之路(第十六篇)xml模块、datetime模块
一.xml模块 xml是实现不同语言或程序之间进行数据交换的协议,跟json差不多,但json使用起来更简单, xml比较早,早期许多软件都是用xml,至今很多传统公司如金融行业的很多系统的接口还主要 ...
- Python之路【第七篇】:常用模块
一. 模块介绍 1. 什么是模块 在前面的几个章节中我们基本上是用 python 解释器来编程,如果你从 Python 解释器退出再进入,那么你定义的所有的方法和变量就都消失了. 为此 Python ...
- Python之路【第四篇】:模块
什么是模块: 模块就是一个功能的集合. 模块就和乐高积木差不多,你用这些模块组合出一个模型,然后也可以用这个模块加上其他的模块组合成一个新的模型 模块的种类: 1.内置模块(python自带的比如os ...
- Python之路【第三篇】:模块
定义: 包:包含__init__.py文件.模块(也是.py文件) 当包被其它模块调用时,首先会执行该包下的__init__文件 包含有模块,包可以有多级 模块的导入: import from...i ...
- Python学习【第十二篇】模块(2)
序列化 1.什么是python序列化? 把变量从内存中变成可存储或传输的过程称之为序列化,在Python中叫pickling 序列化就是将python的数据类型转换成字符串 反序列化就是将字符串转换成 ...
- Python之路(第二十九篇) 面向对象进阶:内置方法补充、异常处理
一.__new__方法 __init__()是初始化方法,__new__()方法是构造方法,创建一个新的对象 实例化对象的时候,调用__init__()初始化之前,先调用了__new__()方法 __ ...
- Python之路(第二十八篇) 面向对象进阶:类的装饰器、元类
一.类的装饰器 类作为一个对象,也可以被装饰. 例子 def wrap(obj): print("装饰器-----") obj.x = 1 obj.y = 3 obj.z = 5 ...
随机推荐
- Windows Server2012 R2 安装.NET Framework 3.5失败解决方法
转载:https://blog.csdn.net/F12138_/article/details/80220698 显示需要指定备用路径,但我没有指定 然后就出现了的失败T T! 由于我无法访问安装盘 ...
- 全国绿色计算大赛 模拟赛第一阶段(C++)第1关:求和
挑战任务 这次“绿盟杯”大赛,小明作为参赛选手在练习的时候遇到一个问题,他要对一个范围的两个数进行数位的累加,例如有两个数 15,19 则 他们的数位和应该为:1+5+1+6+1+7+1+8+1+9, ...
- TOJ3112: 单词串串烧(回溯)
传送门(<--可以点击的) 时间限制(普通/Java):1000MS/3000MS 内存限制:65536KByte 描述 “单词串串烧”是一款拼词智力游戏,给定4*4的方格,随机取16个 ...
- Mac下环境变量设置错误,导致命令行命令不能使用后的解决办法
1 在命令行中,临时设置环境变量 export PATH=/usr/local/bin:/usr/bin:/bin:/usr/sbin:/sbin 2 各种命令就可以使用了.然后修复错误的环境变量配置 ...
- [剑指Offer]45-把数组排成最小的数
题目链接 https://www.nowcoder.com/practice/8fecd3f8ba334add803bf2a06af1b993?tpId=13&tqId=11185&t ...
- FortiGate常用命令
1.命令结构 config Configure object. 对策略,对象等进行配置 get Get dynamic and system information. 查看相关关对 ...
- dUMP:A new value is to be assigned to the field "<L_BOX>"
DUMP: A new value is to be assigned to the field "<L_BOX>", although this field is e ...
- 路径打印(set以及字符串的相关操作)
题目链接 题目描述 给你一串路径,譬如: a\b\c a\d\e b\cst d\ 你把这些路径中蕴含的目录结构给画出来,子目录直接列在父目录下面,并比父目录向右缩一格,就像这样: a b ...
- 同种类型不同名字的变量在for循环中操作
InfoViewController * info = [[InfoViewController alloc] init]; HeroViewController * hero = [[HeroVie ...
- Bootstrap(7) 输入框和导航组件
一.输入框组件 文本输入框就是可以在<input>元素前后加上文字或按钮,可以实现对表单控件的扩展. //在左侧添加文字 <!-- //在左侧添加文字 --> ...