真锋
永远保持一颗学习和专注的心
嵌入式视觉笔记

Python3 编程笔记

这篇文档来自平时项目和学习过程中总结的 Python 知识点

代码报错:IndentationError: expected an indented block分析

python代码有冒号的地方,一定要有缩进啊!!!

函数或者变量带下划线的意义

变量:

  1. 前带 _ 的变量: 标明是一个私有变量, 只用于标明, 外部类还是可以访问到这个变量
  2. 前带两个 _ ,后带两个 _ 的变量: 标明是内置变量,
  3. 大写加下划线的变量: 标明是 不会发生改变的全局变量

python 函数:

  1. 前带 _ 的变量: 标明是一个私有函数, 只用于标明,
  2. 前带两个 _ ,后带两个 _ 的函数: 标明是特殊函数

读取文件三种方式

python 读取文件有三种方法:read(), readline(), radlines()

  • read():直接读取出字符串,并且字符串或者字符对象返回。
  • readline():读取文本中的一行。
  • readlines():读取文本中的所有内容并放入缓存区,返回列表。

collections模块

collections 是python内建的一个集合模块,提供了许多有用的集合类。OrderedDict 可以实现一个 FIFO(先进先出)的 dict,当容量超出限制时,先删除最早添加的 Key。

file()函数

file() 函数用于创建一个 file 对象,用法:file(name[, mode[, buffering]]):

  • name — 文件名
  • mode — 打开模式
  • buffering — 0 表示不缓冲,如果为1表示进行缓冲,大于1为缓冲区大小

返回值:
  文件对象

内置函数

Python3 的内置函数

__init__.py 文件的作用

每一个包目录下面都会有一个 __init__.py 的文件,这个文件是必须存在的,否则, Python 就把这个目录当成普通目录,而不是一个包。

判断键是否存在于字典中

  • if key in dict():通过 in 判断 key 是否存在
  • dict.get(key, value):是通过 dict 提供的 get 方法,如果 key 不存在,可以返回 None,或者自己指定的 value。

异或运算

&, |, ^ 表示二进制的 AND, OR, XOR 运算

内建函数 isalnum()

Python 的 isalnum()方法检测字符串是否由字母和数字组成。

内建函数 callable()

python 中的内建函数 callable( ), 可以检查一个对象是否是可调用的

内建函数 any()/all 函数

Python 有很多内建函数,any() 和 all() 两个函数用于判断给定的 iterable 可迭代对对象是否全为空和是否全不为空,其函数解释如下:

  • any():判断一个 tuple 或者 list 是否全为空、0、False。如果全为空,0,False,则返回 False;如果不全为空,则返回 True。
  • all():all 函数和 any 相反:判断一个tuple或者list是否全为不为空、0、False。如果全不为空,则返回 True;否则返回 False。

实例:用 python 判断一个 string 是否包含一个 list 里的元素。使用 python 的内置函数 any() 会非常简洁:

fruits = ['apple', 'orange', 'peach']
string = "I want some apples"
if any(element in str for element in fruits):
    print ("string contains some the element of fruits list.")

运行结果如下:

deque 双向列表

deque 是为了高效实现插入和删除操作的 双向列表,适合用于队列和栈:

>>> from collections import deque
>>> q = deque(['a', 'b', 'c'])
>>> q.append('x')
>>> q.appendleft('y')
>>> q
deque(['y', 'a', 'b', 'c', 'x'])

deque 除了实现 list 的 append() 和 pop() 外,还支持 appendleft()popleft(),这样就可以非常高效地往头部添加或删除元素,相当于入栈和出栈操作

load yaml文件

# open方法打开直接读出来
f = open(yamlPath, 'r', encoding='utf-8')
cfg = f.read()
print(type(cfg)) # 读出来是字符串
print(cfg)
d = yaml.load(cfg) # 用load方法转字典
print(d)
print(type(d))

获取和设置环境变量

sys.version_info获取python版本号:

sys.version_info(major=2, minor=7, micro=5, releaselevel=’final’, serial=0)

获取环境变量代码如下:

import os
for key in os.environ.keys():
    print(key)

设置环境变量代码(当前设置的环境变量只是在本程序中生效,不是永久更新)如下:

import os
os.environ['PYTHONUNBUFFERED'] = '1'
print(os.environ.get('PYTHONUNBUFFERED'))

python2 xrange函数

xrange() 函数用法与 range 完全相同,所不同的是生成的不是一个数组,而是一个生成器。

内部模块 deque

deque 是为了高效实现插入和删除操作的双向列表,适合用于队列和栈。deque 除了实现 list 的 append()和 pop()外,还支持 appendleft()popleft(),这样就可以非常高效地往头部添加或删除元素。代码示例:

>>> from collections import deque
>>> q = deque(['a', 'b', 'c'])
>>> q.append('x')
>>> q.appendleft('y')
>>> q
deque(['y', 'a', 'b', 'c', 'x'])

用 map 高阶函数返回列表指定元素

def ConvertToLdmk21(ldmks_pts):
  """
  Parameters:
    @ldmks_pts:
      - ldmk_28, nose_idx = 16
  """
  elif len(ldmks_pts) == 28:
    ldmk_28to21 = [0, 1, 2, 3, 4, 5, 6, 10, 8, 11, 15, 13, 17, 16, 18, 19, 20, 23, 24, 22, 21]
    ldmks21 = map(lambda i: ldmks_pts[i], ldmk_28to21)  # 挑选列表中的指定元素
  else:
    print('Error:', __name__, len(ldmks_pts), ldmks_pts)
    return []
  return ldmks21

双冒号 :: 用法

a[i:j:k] 是根据该“片第从 i 到 j 与第 k 步”。何时i和j缺席,整个序列是和 a[::k] 意思是“每 k 个项目”。 示例如下:

>>> s = range(20)
>>> s
[0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 17, 18, 19]
>>> s[::3]
[0, 3, 6, 9, 12, 15, 18]

::分开结束,开始,步长值。特殊地:a[::-1] 相当于 a[-1:-len(a)-1:-1],也就是从最后一个元素到第一个元素复制一遍,即倒序。

获取python解释器路径

import sys
sys.executable

easydict 模块使用

EasyDict 可以让我们像访问属性一样访问 dict 里的变量,示例代码如下:

>>> from easydict import EasyDict as edict
>>> d = edict({'a':123, 'b':234, 'c':345})
>>> d.a
123

file flush()方法

概述flush() 方法是用来刷新缓冲区的,即将缓冲区中的数据立刻写入文件,同时清空缓冲区,不需要是被动的等待输出缓冲区写入。一般情况下,文件关闭后会自动刷新缓冲区,但有时你需要在关闭前刷新它,这时就可以使用 flush() 方法。
语法fileObject.flush()
返回值:该方法无返回值。

global 关键字作用

根据一个变量起作用的范围不同,可以将变量分为全局变量与局部变量:

  • 全局变量在全局范围内起作用,局部变量在一个函数内部起作用
  • 一般全局变量是不可以更改的,但是在 python 中,可以使用 global 关键字进行更改,更改后的全局变量将以新的值在全局范围内继续起作用。
  • global关键字:声明此变量为全局变量
  • 在一个函数中,对全局变量进行修改的时候,是否需要使用 global 进行说明要看是否对全局变量的执行指向进行了修改如果修改了执行指向,即让全局变量指向了一个新的地方,那么必须使用 global,如果仅仅是修改了指向的空间中的数据,此时不需要使用 global。

函数参数

  • 可变参数:可变参数就是传入的参数个数是可变的,把参数组装为 list 或者 tuple 传进函数,可变参数在参数前面加*号,在函数内部,可变参数自动组装为一个 tuple。示例代码如下:
def calc(*numbers):
    sum = 0
    for n in numbers:
        sum = sum + n * n
    return sum
  • 关键字参数:关键字参数允许你传入 0 个或任意个含参数名的参数,这些关键字参数在函数内部自动组装为一个 dict。和可变参数类似,也可以先组装出一个 dict,然后,把该 dict 转换为关键字参数传进去。

Python3 与 Python2 range 函数

  • Python3 range() 函数返回的是一个可迭代对象(类型是对象),而不是列表类型, 所以打印的时候不会打印列表。
  • Python2 range() 函数返回的是列表

使用@property

@property 的作用就是:把类的方法转化为类的属性(只读)、取代传统的 get/set/del 方法。

实例属性和类属性

由于 Python 是动态语言,根据类创建的实例可以任意绑定属性。给类实例绑定属性的方法是通过实例变量,或者通过 self 变量。类本身需要绑定一个属性,可以直接在 class 中定义属性,这种属性是类属性,归 Student 类所有。代码实例如下:

class Student(object):
    def __init__(self, name):
        self.name = name

s = Student('Bob')
s.score = 90 

EasyDict使用

from easydict import EasyDict,EasyDict 可以让你像访问属性一样访问字典 dict 里的变量。

偏函数创建

  • functools.partial 可以帮助我们创建一个偏函数, functools.partial 的作用就是,把一个函数的某些参数给固定住(也就是设置默认值),返回一个新的函数,调用这个新函数会更简单。
  • 创建偏函数时,实际上可以接收函数对象、 args*kw 这 3 个参数。
  • 当函数的参数个数太多,需要简化时,使用 functools.partial 可以创建一个新的函数,这个新函数可以固定住原函数的部分参数,从而在调用时更简单。
import functools
int2 = functools.partial(int, base=2)  # 将传入2进制变量转化为10进制整数
print('1000000 =', int2('1000000'))  # ('1000000 =', 64)
print('1010101 =', int2('1010101'))  # ('1000000 =', 85)

print输出多行内容

  • python 允许用 '''...''' 的格式表示多行内容
  • 也可以用 \n 实现
print '''
Usage: python crop_to_small_images.py data_type data_name save_dir class_type
       data_type -- 'train' or 'test'
'''

程序输出

Usage: python crop_to_small_images.py data_type data_name save_dir class_type
data_type — ‘train’ or ‘test’

file writelines方法

writelines() 方法用于向文件中写入一序列的字符串。这一序列字符串可以是由迭代对象产生的,如一个字符串列表。换行需要制定换行符 \n。

global语句使用

python中定义函数时,若想在函数内部对函数外的变量进行操作,就需要在函数内部声明其为global。

获取当前日期模块 datetime

datetime: 日期时间模块,提供多种方法操作日期和时间
strftime: 对日期时间格式化,可格式化为字符串

>>> import datetime
>>> today = datetime.date.today()
>>> print(today)
2019-06-11
>>> type(today)
<class 'datetime.date'>
>>> formatted_today = today.strftime('%y%m%d')
>>> print(formatted_today)
190611
>>> type(formatted_today)
<class 'str'>

json数据解析

  • json.dumps(): 对数据进行编码
  • json.loads(): 对数据进行解码

如果要处理的是文件而不是字符串,你可以使用 json.dump()json.load() 来编码和解码 JSON 文件数据。实例代码如下:

# 写入 JSON 数据
with open('data.json', 'w') as f:
    json.dump(data, f)
# 读取数据
with open('data.json', 'r') as f:
    data = json.load(f)

if continue语句

  • continue 是跳出本次循环
  • break 是跳出整个循环

os.walk() 函数

os.walk(top, topdown=True, onerror=None, followlinks=False)

可以得到一个三元 tupple(dirpath, dirnames, filenames) generator,可 for 循环遍历这个 generaor,得到所有目录(包括子目录)的三元 tuple。
第一个为起始路径,第二个为起始路径下的文件夹,第三个是起始路径下的文件。

  • dirpath 是一个 string,代表目录的路径,
  • dirnames 是一个 list,包含了dirpath下所有子目录的名字。
  • filenames 是一个 list,包含了非目录文件的名字。
    os.walk(root_dir) 先遍历 root_dir 目录下的第一个子目录,再依次遍历第二、第三、第 n 个目录,每遍历一个子目录都得到一个 generator。

实例-python获取文件夹大小

import os
f_dir = os.path.abspath(os.path.dirname(__file__))
def get_dir_size(dir):
    size = 0
    for root, dirs, files in os.walk(dir):
        size += sum([os.path.getsize(os.path.join(root, name)) for name in files])
    return size
if __name__ == '__main__':
    size = get_dir_size('../')
    print('Total size is: %.3f Mb'%(size/1024/1024))

os.mkdir函数与os.makedirs函数

path = '/test/path_01/path_02/path03/'
  • os.mkdir 函数只会创建 path 路径的最后一级目录
  • os.makedirs 函数创建多层目录,如果 path 的四级目录都没有,则会自动递归创建全部 test、path_01、path_02、path_0 3这 4 个目录。

sys.argv 用法

sys.argv[] 用来获取命令行参数,sys.argv[0] 表示文件路径本身,所以参数是从 sys.argv[1] 开始

super() 函数

深入理解 super() 函数在类的继承中,如果重定义某个方法,该方法会覆盖父类的同名方法,但有时,我们希望能同时实现父类的功能,这时,我们就需要调用父类的方法了,可通过使用 super() 函数来实现。
描述:

  • super() 函数是用于调用父类(超类)的一个方法
  • super 是用来解决多重继承问题的,直接用类名调用父类方法在使用单继承的时候没问题,但是如果使用多继承,会涉及到查找顺序(MRO)、重复调用(钻石继承)等种种问题。
  • MRO 就是类的方法解析顺序表, 其实也就是继承父类方法时的顺序表。

语法:

super(type[, object-or-type])

参数:

  • type – 类。
  • object-or-type – 类,一般是 self

实例如下:

class A:
    def __init__(self):
        print("A")
class B(A):
    def __init__(self):
        print("B")
        super().__init__() # 调用父类
if __name__ == '__main__':
    b = B()

输出结果:

B
A # super调用父类输出 A

赞赏

发表评论

textsms
account_circle
email

嵌入式视觉笔记

Python3 编程笔记
这篇文档来自平时项目和学习过程中总结的 Python 知识点 代码报错:IndentationError: expected an indented block分析 python代码有冒号的地方,一定要有缩进啊!!! 函数或者…
扫描二维码继续阅读
2020-09-10