面向对象

类的创建与实例化

  • 代码

    1
    2
    3
    4
    5
    6
    7
    8
    class Student():  # 创建一个类
    name = ''
    age = 0

    def print_file(self): # 类中的函数
    pass

    student = Student() # 类的实例化
  • 方法函数 有何区别?

    方法:设计层面的说法

    函数:程序运行、过程的一种称谓

构造函数

  • 无参构造函数

    1
    2
    def __init__(self):
    pass
  • 有参构造函数

    1
    2
    3
    def __init__(self,name,age):
    self.name = name;
    self.age = age;

类变量与实例变量

  • 举例

    1
    2
    3
    4
    5
    6
    7
    8
    9
    class Student():
    sum = 0; # 类变量的赋值,Student.sum即可访问
    name = ''
    age = 0

    def __init__(self,name,age):
    self.name = name # 实例变量的赋值
    self.age = age # 类内访问类变量需要加self,在类外访问为 对象名.变量名
    print(self.__class__.sum) # 第二种调用方法
  • 检测实例变量

    1
    2
    # className为类名
    className.__dict__

类方法

  • 定义方式

    1
    2
    3
    4
    5
    # 若添加了这个装饰器,与self还是cls无关(可替换)
    @classmethod
    def plus_sum(cls):
    cls.sum += 1
    print(cls.sum)

私有与公开方法、成员

  • 若要表示该方法为私有,在方法名前加 __ 即可,例如

    1
    2
    def __marking(self, score):
    self.score = score;
  • 若要表示该方法为公开,默认即可,或者前后均加上 __

  • 可通过特殊方法在类外强制访问私有成员(不建议)

    1
    2
    #例如
    print(student2._Student__score)

封装、继承、多态——三大特性

  • 继承(继承父类变量与方法)

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    # 继承举例,父类People,子类Student

    class People():
    sum = 0
    def __init__(self, name, age):
    self.name = name
    self.age = age

    class Student(People):
    def __init__(self,school,name,age):
    self.school = school
    People.__init__(self,name,age)
    # 注意调用父类构造函数要传入self
    # super(Student, self).__init__(name, age)
    # super关键字用来调用父类成员和方法
  • 若上面使用super的方式,代码运行后会出现错误:

    1
    TypeError: super() argument 1 must be type, not classobj
  • 原因:注意,super方法只能用于新类,即必须有继承的类,下面是经典类的举例

    1
    2
    class People():
    ....
  • 若要将上述类变为新类(加上继承关系),可改为:

    1
    2
    class People(object):
    .....

正则表达式

什么是正则表达式

  • 正则表达式(regular expression)描述了一种字符串匹配的模式(pattern) , 用以检查字符串

  • 正则表达式举例

    1
    2
    3
    4
    5
    6
    import re
    a = 'C2C++3Java4C#5Python6Javascript'
    print(re.findall('\d',a)) #'\d'代表所有数字字符

    #结果:
    ['2', '3', '4', '5', '6']

普通字符与元字符

  • 元字符代表抽象的字符串,正则表达式的学习与元字符息息相关

  • 例如:‘ Python’ 为普通字符,‘\d’为元字符

  • 查看更多元字符 点击这里

字符集

  • 抽象出要查找的字符(串)的特性

  • 使用中括号 [] ,表示’或’关系

  • 例如

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    import re
    s = "abc, acc, adc, aec, afc, ahc"
    r = re.findall('a[cf]c',s)
    print(r)

    #结果:
    ['acc', 'afc']

    import re
    s = "abc, acc, adc, aec, afc, ahc"
    r = re.findall('a[^cf]c',s)
    print(r)

    #结果:
    ['abc', 'adc', 'aec', 'ahc']
  • 概括字符集:可用字符集来表达的元字符

    1
    2
    3
    #例如
    '\d' 等同于 '[0-9]'
    '\w' 等同于 '[a-zA-Z0-9_]' #单词字符
  • 正则表达式常用的字符集:点击这里

数量词

  • 使用{ }指定前一个字符集或字符出现的次数

    1
    2
    3
    4
    5
    6
    import re
    a = 'java 4 C# 5 python 6 & php'
    print(re.findall('[a-z]{3,6}',a))

    #结果
    ['java', 'python', 'php']
  • 贪婪非贪婪 的匹配机制

    • 默认情况下,Python使用贪婪机制,即尽可能满足某个条件

    • 若使用非贪婪在数量词后加 ? 即可

      1
      2
      3
      4
      5
      6
      import re
      a = 'java 4 C# 5 python 6 & php'
      print(re.findall('[a-z]{3,6}?',a))

      #结果
      ['jav', 'pyt', 'hon', 'php']
  • 匹配0次、1次、无限多次

    • 使用 * 匹配前一个字符(集)0次或无限多次

      1
      2
      3
      4
      5
      6
      import re
      a = 'pytho0python1pythonn2'
      print(re.findall('python*',a))

      #结果
      ['pytho', 'python', 'pythonn']
    • 使用 + 匹配前一个字符(集)1次或无限多次

      1
      ['python', 'pythonn']
    • 使用 ? 匹配前一个字符(集)0次或1次

      1
      ['pytho', 'python', 'python']

边界匹配

  • 用以匹配整个字符串

  • 在表达式前加 ^ ,在表达式后加 $,例如:

    1
    2
    3
    4
    5
    6
    7
    import re
    qq = "798998087"
    re.findall('^\d{4,8}$',qq)
    print(r)

    #结果,^代表从头匹配,$代表从末尾匹配
    []

  • 使用圆括号 () ,表示’且’的关系

    1
    re.findall('(Python)',a)

匹配模式参数

  • re.I模式举例:忽略正则表达式字母大小写

    1
    2
    3
    4
    5
    6
    import re
    a = 'PythonC#JavaPHP'
    print(re.findall('c#',a,re.I))

    #结果
    ['C#']
  • 若要用多种模式,将不同模式用 | 连接即可

re.sub用以正则替换

  • 代码举例

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    #coding=utf-8
    import re
    language = 'PythonC#PHPC#JAVA'

    #参数1:正则表达式,参数2:要替换成的字符串(也可以是函数),参数3:被搜索的字符串,参数4:替换模式 0为全替换,n为替换n个
    r = re.sub('C#','GO',language,1)
    print(r)

    #结果
    'PythonGOPHPC#JAVA'
  • 通过函数判断并替换字符

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    import re
    s = 'A8C3721D86'

    def convert(value):
    matched = value.group()
    if int(matched) >=6 :
    return '9'
    else:
    return '0'

    r = re.sub('\d',convert,s)
    print(r)

    #结果
    A9C0900D99

re.match与re.search : 匹配成功一次则返回

  • re.match从字符串首字母开始匹配,若头部不满足条件则返回None
  • re.search搜索整个字符串
  • 可使用span()函数获得匹配成功的字符位置

获取字符串中间内容

  • 代码参考

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    import re

    s = "life is short , i use python"

    r1 = re.search('life(.*)python', s)
    #r2 = re.findall('life(.*)python',s) 使用括号表达正则表达式分组

    print(r1.group(1))
    #print(r2)

    #结果
    is short , i use
  • 总结:对于search函数来说,使用group(n)来访问正则表达式的分组,若n=0,返回全部分组匹配结果,否则返回第n个分组匹配内容

JSON

什么是JSON

  • JavaScript Object Notation

  • 一种轻量级的数据 交换格式

  • 字符串 是JSON的表现形式

  • 什么是JSON字符串?

    符合JSON格式的字符串叫做JSON字符串,如:

    1
    {"name":"ba-nana"}

Python接收JSON字符串 (反序列化)

  • 代码参考

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    import json

    #注意单双引号
    json_str='{"name":"banana", "age":19}' #一个JSON object
    student = json.loads(json_str)

    print(type(student))
    print(student)
    print(student['age']) #访问字典内容

    #结果
    <type 'dict'>
    {'age': 19, 'name': 'banana'}
    19
  • 若接收的JSON字符串为数组

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    import json

    #多个JSON object组成数组
    json_str='[{"name":"banana", "age":19},{"name":"salaka", "age":18}]'

    student = json.loads(json_str)

    print(type(student))
    print(student)
    print(student[0]["name"])

    #结果
    <type 'list'>
    [{'age': 19, 'name': 'banana'}, {'age': 18, 'name': 'salaka'}]
    banana
  • JSON -> Python常见的数据转换格式

    JSON Python
    object dict
    array list
    string str
    number int
    number float
    true True
    false False
    null None

序列化 Python -> JSON

  • 代码参考

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    import json

    student = [
    {'name':'banana','age':19,'flag':False},
    {'name':'salaka','age':18}
    ]

    print(type(student))
    #序列化
    json_str = json.dumps(student)
    print(json_str)

    #结果
    <type 'list'>
    [{"age": 19, "flag": false, "name": "banana"}, {"age": 18, "name": "salaka"}]

Python的高级语法与用法

枚举

  • 枚举的定义

    1
    2
    3
    4
    5
    6
    7
    8
    from enum import Enum
    #from enum import IntEnum 与上面不同,枚举类型只能为Int

    class VIP(Enum):
    YELLOW = 1
    BLACK = 2
    GREEN = 3
    RED = '4'
  • 访问枚举名与值

    1
    2
    3
    #访问枚举成员GREEN为示例
    VIP.GREEN.name #访问枚举名
    VIP.GREEN.value #访问枚举值
  • 枚举的比较

    • 可以做身份(is)和等值(==)比较
    • 不可以做大小比较
  • 枚举的遍历

    1
    2
    3
    4
    5
    6
    7
    8
    #获取枚举值与名字
    for x in VIP:
    print(x.value)
    #print(x.name)

    #获取所有枚举
    for x in VIP.__members__.items():
    print(x)
  • 枚举类型转换

    1
    2
    3
    4
    5
    6
    #数字 -> 枚举类型
    a = 1
    r = VIP(a)
    print(r)
    #结果
    VIP.YELLOW
  • 枚举唯一值装饰器

    1
    2
    3
    4
    from enum import Enum,unique
    @unique
    class(Enum)
    pass

闭包

  • 函数+环境变量 -> 闭包

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    def curve_pre():
    a = 25 #环境变量
    def curve(x):
    return a*x*x
    return curve

    a = 10 #外部变量
    f = curve_pre()
    print(f(2))

    #结果(形成闭包后不受外部变量改变影响)
    100
  • 查看闭包参数

    1
    2
    3
    4
    5
    6
    7
    f = curve_pre()
    print(f.__closure__) #若没有闭包,会返回None
    print(f.__closure__[0].cell_contents)

    #结果
    (<cell at 0x1060d6670: int object at 0x7fb40bd05388>,)
    25
  • 解决一个实例问题——累加

    • 非闭包方法

      1
      2
      3
      4
      5
      6
      7
      8
      9
      10
      11
      origin = 0

      def go(step):
      global origin #若没全局变量声明,下面会报错,origin会被默认为局部变量
      new_pos = origin + step
      origin = new_pos
      return new_pos

      print(go(2)) #2
      print(go(3)) #5
      print(go(4)) #9
    • 闭包方法:不修改全局变量,保存现场 的功能

      1
      2
      3
      4
      5
      6
      7
      8
      9
      10
      11
      12
      13
      14
      origin = 0

      def factory(pos):
      def go(step):
      nonlocal pos
      new_pos = pos + step
      pos = step
      return new_pos
      return go

      tourist = factory(origin)

      print(tourist(2)) #2
      print(tourist(3)) #5

函数式编程

匿名函数

  • 声明

    1
    lambda parameter_list: expression
  • 示例

    1
    2
    3
    4
    5
    6
    def add(x, y):
    return x+y
    add(1,2)

    f = lambda x,y: x+y #匿名函数的声明
    f(1,2) #匿名函数的调用

三元表达式

  • 相对于其他编程语言(Java为例)

    1
    2
    //Java中
    x > y ? x : y
  • Python中的三元表达式略有不同

    1
    2
    #Python中
    x if x > y else y

map

  • 用于多次执行函数 (映射),分别传入方法与列表(可多个列表)

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    list_x = [1,2,3,4,5,6,7,8]

    def square(x):
    return x*x

    r = map(square, list_x)
    # for x in list_x:
    # 等同于下列for循环
    # square(x)
    print(r)

    #结果
    [1, 4, 9, 16, 25, 36, 49, 64]
  • 当lambda和map结合

    1
    2
    3
    4
    5
    list_x = [1,2,3,4,5,6,7,8]
    r = map(lambda x: x*x, list_x)
    print(r)

    #结果与上个代码块相同

reduce

  • 元素递减运算(归约)

    1
    2
    3
    4
    5
    6
    #例子
    list_x = [1,2,3,4,5,6,7,8]

    r = reduce(lambda x,y:x+y, list_x, 15)

    #上述运算相当于((((15+(1+2))+3)+4)+...

filter

  • 过滤函数

    1
    2
    3
    4
    5
    6
    list_x=[1,0,1,0,1,0]
    r = filter(lambda x: True if x==1 else False, list_x)
    print(r)

    #结果
    [1, 1, 1]

装饰器

  • 装饰器可以增强代码复用性,通常用于业务需求更改

  • 装饰器的定义示例

    1
    2
    3
    4
    5
    6
    import time
    def decorator(func): #形成了闭包
    def wrapper():
    print(time.time())
    func()
    return wrapper
  • 装饰器的调用

    1
    2
    3
    4
    5
    6
    7
    8
    9
    @decorator
    def f1():
    print("this is a function")

    f1()

    #结果
    1581134973.93
    this is a function
  • 为了通用性,要将装饰器传入参数改为 动态的,即:

    1
    2
    3
    4
    5
    6
    import time
    def decorator(func):
    def wrapper(*args): #动态参数,单*号+任意名
    print(time.time())
    func(*args)
    return wrapper
  • 双*号传入混合参数(参数名任意)

    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    import time
    def decorator(func):
    def wrapper(*args,**kw): #此处传入**kw
    print(time.time())
    func(*args,**kw)
    return wrapper

    @decorator
    def f2(func_name1, func_name2, **kw):
    print('1:'+func_name1)
    print('2:'+func_name2)
    print(kw)

    f2('lala','hh',a=2,b=3,c='123')

    #结果
    1581136034.04
    1:lala
    2:hh
    {'a': 2, 'c': '123', 'b': 3} #此处为kw代表的值