美文网首页
Python - Day8

Python - Day8

作者: 姚屹晨 | 来源:发表于2017-10-02 10:09 被阅读17次

廖雪峰:Python教程

一.模块

①在Python中,一个.py文件就称之为一个模块(Module)

②使用模块可以避免函数名和变量名冲突,同名的函数和变量完全可以分别存在于不同的模块中,但是要注意,避免与内置函数名发生冲突。

所有内置函数.png

③如果不同的人编写的模块名相同怎么办?

  • 为了避免模块名冲突,Python引入了按目录来组织模块的方法,称之为包(package)
package.png
1.使用模块

#让该脚本/模块文件在Unix/Linux/Mac上运行
#!/usr/bin/env python3

#表示脚本/模块本身使用标准UTF-8编码
# -*- coding: utf-8 -*-

#任何模块代码的第一个字符串均表示模块的文档注释
'a test module'

#使用__author__变量把作者写进去
__author__ = 'Gerg'

#导入sys模块后,就有了变量sys指向该模块
#通过sys这个变量,就可以访问sys模块的所有功能
import sys

def test():
#sys模块有一个argv变量,用list存储了命令行的所有参数
#argv至少有一个参数,因为第一个参数永远是该.py文件的名称
    args = sys.argv
    if len(args) == 1:
        print('Hello,world!')
    elif len(args) == 2:
        print('Hello,%s' %args[1])
    else:
        print('Too mant arguments!')
#当我们直接运行该模块文件时,Python解释器把一个特殊变量
#__name__置为__main__;但如果在其他地方导入该模块时,
#if判断将失败。运行测试
if __name__ == '__main__':
    test()
1.png

python编程中的if name == 'main': 的作用和原理

.py文件有两种使用的方式:第一种是直接作为脚本运行;另一种是import到其他python脚本中被调用(模块重用)执行。

if __name__ == ''__main___":只有在第一种情况下(即文件作为脚本直接执行)才会被执行。

第一种作为脚本直接运行.png 第二种方法import到其他的python脚本中被调用执行.png

③运行的原理

加个print__name__直接运行脚本.png 第二种方法.png
  • 注:每个python模块(脚本,这里就是test.pyimport_test.py)都包含内置的变量__name__,当模块被直接运行时,__name__等于文件名(包含后缀.py);如果import到其他模块中,则__name__等于模块名(不包含后缀.py)。而"__main__"等于当前执行文件的名称(包含了后缀.py)。
2.作用域

①正常的函数和变量名都是公开的(public),可以被直接引用。

②类似__xxx__这样的变量是特殊变量,可以被直接引用,但有特殊的用途。

③类似_xxx__xxx这样的函数或变量就是非公开的(private),不应该被直接引用。

④外部不需要引用的函数全部定义为private,只有外部需要引用的函数才定义为public

3.安装第三方模块

①在Python中,安装第三方模块,是通过包管理工具pip完成的。

二.面向对象编程(Object Oriented Programming)

①把对象作为程序的基本单元,一个对象包含了数据和操作数据的函数。

②什么是面向过程的程序设计?

  • 把计算机程序视为一系列的命令集合,即一组函数的顺序执行。为了简化程序设计,面向过程把函数继续切分为若干子函数。

③什么是面向对象的程序设计?

  • 把计算机程序视为一组对象的集合,每个对象都可以接收其他对象发送过来的消息,并处理这些消息,计算机程序的执行就是一系列消息在各个对象之间传递。

④在Python中,所有数据类型都可以视为对象,当然也可以自定义对象。自定义的对象数据类型就是面向对象中的类(Class)的概念。

⑤面向过程和面对对象在程序流程上的不同?

  • 面向过程:
面向过程.png
  • 面向对象:(给对象发消息,实际上就是调用对象对应的关联函数,称之为方法(Method)
面向对象内包含数据和操作数据的方法.png
  • 面向对象的设计思想是抽离出Class,根据Class创建Instance

  • 面向对象的抽象程序要比函数更高,因为一个Class既包含数据,又包含了操作数据的方法。

  • 面向对象的三大特点:数据封装、继承和多态

1.类(Class)和实例(Instance)

①如何创建实例?

类型+()创建实例.png

②由于类可以起到模板的作用,因此,可以在创建实例的时候,把一些我们认为必须绑定的属性强制填写进去。通过定义一个特殊的__init__方法,在创建实例的时候,就把namescore等属性绑上去。

class Student(object):
    #__init__方法的第一个参数永远是self,表示创建的实例本身。
    #有了__init__方法,在创建实例的时候,就不能传入空的参数了
    #必选传入与__init__方法匹配的参数,但self不需要传。
    def __init__(self,name,score):
        self.name = name
        self.score = score
__init__.png
2.数据封装

①在Student类中,每个实例都拥有各自的namescore这些数据,既然Student实例本身就拥有这些数据,要访问这些数据,就没有必要从外面的函数去访问,可以直接在Student类的内部定义访问数据的函数,这样,就把"数据"封装起来了。这些封装数据的函数和Student类本身是由关联的,因此,我们称之为类的方法。

数据封装.png

②封装的另一个好处是可以给Student类增加新的方法,如何get_grade

封装数据的另一个好处是可以随时为该类添加新的方法.png
3.小结

①类是创建实例的模板,而实例则是一个一个具体的对象,每个实例拥有的数据互相独立、互不影响。

②方法就是与实例绑定的函数,和普通函数不同,方法可以直接访问实例的数据。

4.访问限制

①虽然将数据和操纵数据的方法都封装进一个类中,但仍可以通过外部代码自由修改一个实例的namescore属性:

仍可以通过外部代码修改类内部的属性.png

②如何做到内部属性不被外部访问?

  • 可以在属性的名称前加上两个下划线__
变量名如果以__开头就变成一个私有变量.png

③但是如果外部代码要获取namescore怎么办?

可以再给类中添加两个方法来获取name和score.png

④如果又想允许外部代码修改score怎么办?

如何修改类中的私有变量.png

⑤其实双下划线开头实例变量不一定不能从外部访问,不能直接访问__name是因为Python解释器对外把__name变量改成了_Student__name,所以,可以通过_Student__name来访问__name变量(强烈不建议那么干,因为不同版本的Python解释器会把__name改成不同的变量名)

实例对象_Student__name.png

⑥一个大坑:

大坑.png
  • 注:其实这个__name变量和Class内部的__name变量不是一个变量!内部的__name变量已经被Python解释器自动改成了_Student__name,而外部代码给person1新增了一个__name变量。
get_name()返回的是内部self__name.png
5.继承和多态

①在OOP程序设计中,当我们定义一个Class时,可以从某个现有的Class继承,新的Class称之为子类(Subclass),而被继承的Class称为基类、父类或超类(Base Class、Super Class)

子类继承父类的方法.png
  • 注:对于Dog来说,Animal就是它的父类;对于Animal来说,Dog就是它的子类。

②继承有什么好处?

  • 最好的好处是子类获得了父类的全部功能。

③当子类和父类存在相同的run()方法时,子类的run()会覆盖了父类的run(),在代码运行的时候,总会调用子类的run()。这样,我们就获得了继承的另一个好处:多态。

多态也就是子类和父类共有一个同名的方法子类会覆盖父类的.png

④当我们定义一个Class的时候,实际上我们就定义了一种数据类型。我们定义的数据类型和Python自带的数据类型,比如strlistdict没有什么两样。

a = list()  #a是list类型
b= Animal() #b是Animal类型
c = Dog()   #c是Dog类型
  • 如何判断一个变量是否是某个类型?
  • isinstance()
isinstance.png

⑤对于一个变量,我们只需知道它是Animal类型,无需确切地知道它的子类型,就可以放心调用run()方法,而具体调用的run()方法是在AnimalDogCat还是Wangba对象上,由运行时该对象的确切类型决定,这就是多态真正的威力:调用方只管调用,不管细节。

多态的威力.png

⑥什么是"鸭子类型"?

  • 它并不要求严格的继承体系,一个对象只要"看起来像鸭子,走起路来像鸭子",那它就可以被看做鸭子。

  • 对于静态语言,如果需要传入Animal类型,则传入的对象必须是Animal类型或它的子类,否则,就无法调用run()方法。

  • 对于Python这样的动态语言,则不一定需要传入Animal类型,只需保证传入的对象由一个run()方法就可以了。

6.获取对象信息

①如何判断对象的类型?

  • type()函数 - 返回对象Class类型
判断对象等类型type.png

②如果要判断一个对象是否是函数怎么办?

  • 可以使用types模块中定义的常量(FunctionType,BuiltinFunctionType,LambdaType,GeneratorType)
如何判断一个对象是否是函数使用types模块中定义的常量.png

isinstance()

isinstance(content,type).png

dir() - 获取一个对象的所有属性和方法。

dir().png

⑤配合getattr()setatter()hasattr(),可以直接操作一个对象的状态。

可以测试对象的属性.png

⑥也可以获得对象的方法(赋值给一个变量)。

获得对象的方法.png
7.实例属性和类属性

①实例属性

实例属性.png

②类属性

类属性.png

③不要把实例属性和类属性使用相同的名字,因为相同名称的实例属性将屏蔽掉类属性,但是当你删除实例属性时,再使用相同的名称,访问的将是类属性。

三.面向对象高级编程

1.使用__slots__(卡槽)

①有什么用?

  • 限制实例的属性。
__slots__是为了限制实例的属性.png

__slots__定义的属性只对当前类实例起作用,对继承的子类是不起作用滴。

__slots__定义的属性对继承的子类不起作用.png
2.使用@property

①在绑定属性时,如果我们直接把属性暴露出去,虽然写起来很简单,但是,没有办法检查参数,导致一些神奇的操作:

s = Student()
s.score = 9999

②为了限制score的范围,可以通过set_score()方法来设置成绩,再通过get_score()方法来获取成绩。

888ValueError.png 88.png

③有没有既能检查参数,又能用类似属性这样简单的方式来访问类的变量呢?

  • Python内置的@property装饰器就是负责把一个方法变成属性调用的。
@property.png 长乘以宽@property.png

相关文章

  • Python自学笔记Day8

    Python自学笔记——Day8 Python运算符 4. 比较运算符 为我们提供比较功能的运算符 最后的结果总是...

  • Python Day8

    1、and ‘and’逻辑符可以将任意表达式连在一起,并返回一个布尔类型的值。 2、while ‘while’后面...

  • Python - Day8

    廖雪峰:Python教程 一.模块 ①在Python中,一个.py文件就称之为一个模块(Module) ②使用模块...

  • python基础-day8

    一、元组 1、什么是元组 元组:使用()将多个元素括起来,多个元素之间用逗号隔开a.容器,可以同时存储多个数据,不...

  • python学习_day8

    高级数据类型 序列:在python中,序列就是一组按照顺序排列的值【数据集合】 在python中存在三种内置的序列...

  • 2018-09-09

    Day8

  • 100天实验

    day8

  • Goodbye my holiday

    day8

  • 今日份摄影作品(运动)

    Day8

  • 卟弃丰盛日记Day8

    卟弃丰盛日记Day8 卟弃今日计划Day8 2020.11.08 不知不觉...

网友评论

      本文标题:Python - Day8

      本文链接:https://www.haomeiwen.com/subject/lhmzextx.html