pip命令的使用
在安装Python时,同时还会安装pip软件,它是Python的包管理工具,可以用来查找、下载、安装和卸载Python的第三方资源包。
配置pip
可以直接在终端中输入pip命令,如果出错,可能会有两个原因:
- pip安装成功以后没有正确配置
- 安装Python时,没有自动安装pip(很少见)
配置pip
和运行Python命令一样,如果想要运行 pip 命令同样也需要将pip命令的安装目录添加到环境变量中。
安装pip
如果在Python安装对应的目录中,没有发现pip.exe文件,可能是因为在安装Python时未自动安装pip,建议将Python卸载,然后在重新安装Python时选择Install Now
使用默认方式安装Python.
管理第三方包
对第三方包的管理主要包含查找、安装和卸载三个部分的操作。
安装
使用 pip install <包名>
命令可以安装指定的第三方资源包。
pip install ipython # 安装ipython包
Copy
使用 install 命令下载第三方资源包时,默认是从 pythonhosted下载,由于各种原因,在国内下载速度相对来说比较慢,在某些时候甚至会出现连接超时的情况,我们可以使用国内镜像来提高下载速度。
临时修改
如果只是想临时修改某个第三方资源包的下载地址,在第三方包名后面添加 -i 参数,再指定下载路径即可,格式为pip install <包名> -i <国内镜像路径>
pip install ipython -i https://pypi.douban.com/simple
Copy
永久修改
除了临时修改pip的下载源以外,我们还能永久改变pip的默认下载路径。
在当前用户目录下创建一个pip的文件夹,然后再在文件夹里创建pip.ini文件并输入一下内容:
[global]
index-url=https://pypi.douban.com/simple
[install]
trusted-host=pypi.douban.com
Copy
常见国内镜像
- 阿里云 https://mirrors.aliyun.com/pypi/simple/
- 中国科技大学 https://pypi.mirrors.ustc.edu.cn/simple/
- 豆瓣(douban) https://pypi.douban.com/simple/
- 清华大学 https://pypi.tuna.tsinghua.edu.cn/simple/
- 中国科学技术大学 https://pypi.mirrors.ustc.edu.cn/simple/
卸载
使用 pip install <包名>
命令可以用来卸载指定的第三方资源包。
pip uninstall ipython # 卸载ipython包
Copy
查找
使用pip list
或者 pip freeze
命令可以来管理第三方资源包。这两个命令的功能一致,都是用来显示当前环境里已经安装的包,区别在于pip list
会列出所有的包,包括一些无法uninstall的包;而pip freeze
只会列出我们安装的第三方包。
总结
开发中,我们通常会使用很多第三方的资源包,我们在将程序部署到服务器的时候,不仅要把代码上传到服务器,同时还需要把代码里用到的第三方资源包告诉服务器。那么这里就有两个问题:
-
当我们电脑上运行很多个项目,每个项目使用的第三方资源包又不一致时,怎样将代码和它使用到的第三方资源包放在一起呢?答:虚拟环境
-
怎样将自己代码使用到的第三方资源包告诉给服务器?
- 使用 pip freeze > requires.txt 命令,将代码里使用到的第三方资源包以及版本号写入到 requirements.txt 文件,在部署时,同时将 requirements.txt 文件上传到服务器。
- 服务器在拿到代码以后,首先运行 pip install -r requirements.txt 命令,将文件里列出的所有第三方框架先安装到服务器,然后才能运行代码。
使用pycharm管理第三方包
除了使用pip 命令管理第三方资源包以外,我们还能使用pycharm来对第三方包进行管理。
自定义模块
除了使用系统提供的内置模块以外,我们还能自己写一个模块供自己的程序使用。一个py文件就是一个模块,所以,自定义模块很简单,基本上相当于创建一个py文件。但是,需要注意的是,如果一个py文件要作为一个模块被别的代码使用,这个py文件的名字一定要遵守标识符的命名规则。
模块的查找路径
创建一个模块非常简单,安装标识符的命名规则创建一个py文件就是一个模块。但是问题是,我们需要把创建好的这个py文件放在哪个位置,在代码中使用 import
语句才能找到这个模块呢?
Python内置sys模块的path属性,列出了程序运行时查找模块的目录,只需要把我们创建好的模块放到这些任意的一个目录里即可。
import sys
print(sys.path)
[
'C:\\Users\\chris\\Desktop\\Test',
'C:\\Users\\chris\\AppData\\Local\\Programs\\Python\\Python37\\python37.zip',
'C:\\Users\\chris\\AppData\\Local\\Programs\\Python\\Python37\\DLLs',
'C:\\Users\\chris\\AppData\\Local\\Programs\\Python\\Python37\\lib',
'C:\\Users\\chris\\AppData\\Local\\Programs\\Python\\Python37',
'C:\\Users\\chris\\AppData\\Roaming\\Python\\Python37\\site-packages',
'C:\\Users\\chris\\AppData\\Local\\Programs\\Python\\Python37\\lib\\site-packages'
]
Copy
__all__
的使用
使用from <模块名> import *
导入一个模块里所有的内容时,本质上是去查找这个模块的__all__
属性,将__all__
属性里声明的所有内容导入。如果这个模块里没有设置__all__
属性,此时才会导入这个模块里的所有内容。
模块里的私有成员
模块里以一个下划线_
开始的变量和函数,是模块里的私有成员,当模块被导入时,以_
开头的变量默认不会被导入。但是它不具有强制性,如果一个代码强行使用以_
开头的变量,有时也可以。但是强烈不建议这样使用,因为有可能会出问题。
总结
test1.py:模块里没有__all__
属性
a = 'hello'
def fn():
print('我是test1模块里的fn函数')
Copy
test2.py:模块里有__all__
属性
x = '你好'
y = 'good'
def foo():
print('我是test2模块里的foo函数')
__all__ = ('x','foo')
Copy
test3.py:模块里有以_
开头的属性
m = '早上好'
_n = '下午好'
def _bar():
print('我是test3里的bar函数')
Copy
demo.py
from test1 import *
from test2 import *
from test3 import *
print(a)
fn()
print(x)
# print(y) 会报错,test2的__all__里没有变量 y
foo()
print(m)
# print(_n) 会报错,导入test3时, _n 不会被导入
import test3
print(test3._n) # 也可以强行使用,但是强烈不建议
Copy
__name__
的使用
在实际开中,当一个开发人员编写完一个模块后,为了让模块能够在项目中达到想要的效果,这个开发人员会自行在py文件中添加一些测试信息,例如:
test1.py
def add(a,b):
return a+b
# 这段代码应该只有直接运行这个文件进行测试时才要执行
# 如果别的代码导入本模块,这段代码不应该被执行
ret = add(12,22)
print('测试的结果是',ret)
Copy
demo.py
import test1.py # 只要导入了tets1.py,就会立刻执行 test1.py 代码,打印测试内容
Copy
为了解决这个问题,python在执行一个文件时有个变量__name__
.在Python中,当直接运行一个py文件时,这个py文件里的__name__
值是__main__
,据此可以判断一个一个py文件是被直接执行还是以模块的形式被导入。
def add(a,b):
return a+b
if __name__ == '__main__': # 只有直接执行这个py文件时,__name__的值才是 __main__
# 以下代码只有直接运行这个文件才会执行,如果是文件被别的代码导入,下面的代码不会执行
ret = add(12,22)
print('测试的结果是',ret)
Copy
注意事项
在自定义模块时,需要注意一点,自定义模块名不要和系统的模块名重名,否则会出现问题!
包的使用
一个模块就是一个 py 文件,在 Python 里为了对模块分类管理,就需要划分不同的文件夹。多个有联系的模块可以将其放到同一个文件夹下,为了称呼方便,一般把 Python 里的一个代码文件夹称为一个包。
1. 导入包的方式
现有以下包newmsg
,包里由两个模块,分别是sendmsg.py
、recvmsg.py
文件。在包的上级文件夹里,有一个test.py
文件,目标是在test.py
文件里引入newmsg
的两个模块。
sendmsg.py文件里的内容如下:
def send_msg():
print('------sendmsg方法被调用了-------')
Copy
recvmsg.py文件里的内容如下:
def recv_msg():
print('-----recvmsg方法被调用了--------')
Copy
可以使用以下几种方式来导入模块,使用模块里的方法。
1>. 直接使用包名.模块模块名导入指定的模块。
2>. 使用from xxx import xxx
方式导入指定模块。
3>. 使用__init__.py
文件,导入包里的指定模块。
可以在newmsg
里创建__init__.py
文件,在该文件里导入指定的内容。
在__init__.py
文件里编写代码:
from . import sendmsg # 导入指定的模块 . 代表的是当前文件夹
Copy
test.py文件里的代码
import newmsg # 导入时,只需要输入包名即可。在包名的__init__.py文件里,导入了指定模块
newmsg.sendmsg.sendm_msg() # 可以直接调用对应的方法
# newmsg.recvmsg.recv_msg() 不可以使用 recvmsg 模块,因为 __init__.py文件里没有导入这个模块
Copy
4.> 使用__init__.py
文件,结合__all__
属性,导入包里的所有模块。
在newmsg
包里的__init__.py
文件里编写代码:
__all__ = ["sendmsg","recvmsg"] # 指定导入的内容
Copy
test.py文件代码:
from newmsg import * # 将newmsg里的__inint__.py文件里,__all__属性对应的所有模块都导入
sendmsg.sendmsg()
recvmsg.recvmsg()
Copy
总结
- 包将有联系的模块组织在一起,即放到同一个文件夹下,并且在这个文件夹创建一个名字为
__init__.py
文件,那么这个文件夹就称之为包
- 有效避免模块名称冲突问题,让应用组织结构更加清晰
2. __init__.py
文件有什么用
__init__.py
控制着包的导入行为。__init__.py
为空仅仅是把这个包导入,不会导入包中的模块。可以在__init__.py
文件中编写内容。
newmsg/__init__.py
文件:
print('hello world')
Copy
别的模块在引入这个包的时候,会自动调用这段代码。
3. __all__
在__init__.py
文件中,定义一个__all__
变量,它控制着 from 包名 import *时导入的模块。
newmsg/__init__.py
文件:
__all__ = ['sendmsg','recvmsg']
Copy