欢迎来到氵一壶灬清酒い的博客

人生三从境界:昨夜西风凋碧树,独上高楼,望尽天涯路。 衣带渐宽终不悔,为伊消得人憔悴。 众里寻他千百度,蓦然回首,那人却在灯火阑珊处。

模块--包

一 模块

1 ; 什么是模块?

常见的场景:一个模块就是包含了python定义和声明的文件,文件名就是模块名字加上.py的后缀.但其实import加载的模块分为四个通用的类别:

  1,使用python编写的代码(.py文件)

  2,已被编译为共享库或DLL的C或C++扩展

  3,包好一组模块的包

  4,使用C编写并链接到python解释器的内置模块

2 为什么要使用模块?

  如果你退出python解释器后重新进入,那么你之前定义的函数或者变量都将丢失;因此我们通常将程序写到文件中以便永久保存下来,需要时就通过python test.py方式去执行,此时test.py被称为脚本script.

  随着程序的发展,功能越来越多,为了方便管理,我们通常将程序分成一个个的文件,这样做程序的解构更清晰,方便管理.这时我们不仅仅可以把这些文件当脚本去执行,还可以把他们当做模块来导入到其他模块当中,实现了功能的重复利用.

3,如何使用模块?

3.1  import

示例文件: 自定义模块my_module.py , 文件名my_module.py,模块名my_module

#my_module.py
print('from the my_module.py')

money = 1000

def read1():
    print('my_moudle->read1->money',money)

def read2():
    print('my_module->read2 calling read1')
    read1()

def change():
    global money
    money = 0

3.1.1

  模块可以包含可执行的语句和函数的定义,这些语句的目的是初始化模块,他们只在模块名第一次遇到导入import语句时才执行(import语句是可以在程序中任意位置使用的,且针对同一个模块import多次,为了防止你重复导入,python的优化手段是:第一次导入后就将模块名加载到内存中.后续的import语句仅是对已加载大内存中的模块对象增加一次引用,不会重新执行模块内的语句))

#demo.py
import my_module  #只在第一次导入时才被执行my_module.py内代码,此处的显示效果只打印一次'from the my_module.py',当然其他的顶级代码也都被执行了,只不过没有显示效果.

import my_module
import my_module
import my_module


'''
执行结果:
from the my_module.py
'''
View Code

3.1.2

  被导入的模块有独立的名称空间

每个模块都是一个独立的名称空间,定义在这个模块中的函数,把这个模块的名称空间当做全局名称空间,这样我们在编写自己的模块时,就不用担心我们定义在自己模块中全局变量会在被导入时,与使用者的全局变量冲突;

  

#test.py
import spam
money = 10
print(spam.money)

'''
执行结果:
form the spam.py
1000
'''
测试一:money与spam.money不冲突
#test.py
import spam
import spam
def reada():
        print('=====')
spam.read1()

'''
执行结果:
form the spam.py
spam->read1->money 1000
'''
测试二:read1与spam.read1不冲突
#test.py
import spam
money = 1
spam.change()
print(money)

'''
执行结果:
from the spam.py
1
'''
测试三:执行spam.change()操作的全局变量money仍然是spam中的

3.1.3

  为模块名起别名    as语句

为已经导入的模块起别名的方式对编写可扩展的代码很有用

import spam as sm

print(sm.money)

3.1.4      

  在一行导入多个模块

import sys,os,re

 

3.2    使用模块之 from...import...

3.2.1

  from...import...的使用

from spam import read1,read2

3.2.2   

  from...import与import的对比

#唯一的区别就是:使用from...import...则是将spam中的名字直接导入到当前的名称空间中,所以在当前名称空间中使用名字就可以了,无需加前缀:spam.

#from...import...的方式有好处也有缺点
    好处:使用起来方便
    坏处:容易与当前执行文件中的名字冲突

当前位置直接使用read1和read2就好了,执行时,仍然以spam.py文件全局名称空间

#测试一:导入的函数read1,执行时仍然回到spam.py中寻找全局变量money
#test.py
from spam import read1
money = 1000
read1()

'''
执行结果:
from the spam.py
spam->read1->money 1000
'''

#测试二:导入的函数read2,执行时需要调用read1(),仍然回到spam.py中找read1()
#test.py
from spam import read2
def read1():
    print('======')
read2()

'''
执行结果:
from the spam.py
spam->read2 calling read
spam->read1->money 1000
'''
View Code

如果当前有重名read1或者read2,那么会产生覆盖效果

导入的方法在执行时,始终是以源文件为准

4.支持as

from spam import read1 as read

5.一行导入多个名字

from spam import read1,read2,money

6.from...import*

#from spam import*   *把spam中所有的不是以下划线(_)开头的名字都导入到当前位置

#大部分情况下我们的python程序不应该使用这种导入方式,因为*你不知道导入什么名字,很有可能覆盖掉你之前已经定义的名字.而且可读性极差,在交互环境中导入时没有问题.

可以使用__all__来控制*(用来发布新版本),在spam.py中新增一行

__all__ = ['money','read1']   #这样在另外一个文件中使用from spam import* 就这样导入列表中规定的两个名字

7.模块引用中的情况:

  1,模块的循环引用

    模块之间不允许循环引用

  2.模块的加载与修改

    已经被导入的模块发生了修改,是不会被感知到的

    要想修改的模块被正在运行中的程序感知到,重启这个程序

  3.把模块当成脚本执行

    if __name__ == '__main__':

       代码

    写在这里的代码只有这个文件被当做脚本执行的时候才被执行

  4.模块的搜索路径

    和被当做脚本执行的文件 同目录下的模块,可以被直接导入

    除此之外其他路径下的模块在被导入需要自己修改sys.path列表

posted on 2018-08-23 19:39  成伤大大  阅读(106)  评论(0编辑  收藏  举报

导航