1、搭建Python开发环境
1.1.1 Python语言的特点
- 简单易学
- 易于阅读
- 免费、开源
- 高级语言
- 可移植性
- 面向对象
- 解析性
- 可扩展可嵌入性
1.1.2 Python语言的版本(使用Python3)
1.1.3Python的应用场景
- 常规软件开发
- 科学计算
- 系统管理与自动化运维
- 云计算
- web开发
- 游戏
- 网络爬虫
- 数据分析
- 人工智能
1.1.4 Python开发环境安装和配置
- 使用Python安装程序安装(直接安装,以后用的第三方库要一个个安装)
- 为什么选择Anaconda
省时省力:Anaconda通过管理工具包、开发环境、Python版本,大大简化了工作流程不仅可以方便的安装、更新、卸载工具包,而且安装时可以自动安装相应的依赖包。
分析利器:Anaconda是适用于企业级大数据的Python工具,其包含了众多与数据科学相关的开源包,涉及数据可视化、机器学习、深度学习等多个方面。 - 安装Anaconda
1.2.2 PyCharm集成开发环境
- Python集成开发环境
(1)Jupyter Notebook 是一个交互式笔记本,支持40多种编程语言。
(2)PyCharm是JetBrains公司开发的Python集成开发环境(一般使用这个) - 安装配置PyCharm集成开发环境(自行百度如何关联Anaconda)
Python文件以.py结尾;
Python的注释:
- 单行注释:以“#”开始,后面是代码的说明内容。例如:#你好 快捷键:选中内容按Ctrl+/
- 多行注释:以’’‘开始,’’'结尾或者以""“开始,”"“结尾,说明内容分布在多行,例如:”"“你好”""
变量与数据类型
2.1.1变量和数据类型
语法:变量名=值
说明:变量不需要声明数据类型,其类型在赋值的那一刻被初始化。
命名规则:
- 变量名长度不限,其中的字符只能是英文字母、数字或者下划线“_”,而不能使用空格、连接符、标点符号、引号或其他符号
- 变量名的第一个字符不能是数字,而必须是字母或下划线
- Python区分大小写
- 不能将Python关键字作为变量名,例如and、del、return等
- 变量名尽量做到“见名知意
同时给多个变量赋值,多个变量之间使用“,”隔开
语法:(1)变量名1[,变量名2,…,变量名n]=值
(2)变量名1[,变量名2,…,变量名n]=值1[,值2,…,值n] 变量名需要与变量值一一对应,如果没有一一对应,程序将会报错。
2.数据类型:Python常见基础数据类型是:整型、浮点型、布尔型和字符串类型。
- 整型:整型就是整数,int表示
- 浮点型:用于表示实数,通俗来说就是带小数点的数,用float表示
- 布尔型:布尔型是特殊的整型,用bool表示,它的值有True和False,如果将布尔值用于数值运算,True会被当作是整数1,Fasle会被当作整数0
- 字符串类型:字符串表示一种文本的数据类型,使用str来表示,字符串有3种创建方式,分别使用单引号、双引号和三引号,3种方式创建的字符串没有区别;注意:在字符串中,如果要让字符输出换行,或者字符串中包含“’”引号,需要用到字符串的转义字符“\”,单个反斜杠转义字符串表示之后的一个字符没有特殊含义。
转义字符:\(在行尾时):续行符
\:反斜杠符号
':单引号
":双引号
\a: 响铃
\b:退格(Backspace)
\e: 转义
\000: 空
\n: 换行
\v: 纵向制表符
\t: 横向制表符,空4个字符位置,等效于tab
\r: 回车
\f: 换页
\oyy: 八进制数yy代表的字符,例如:\o12代表换行
\xyy: 十进制yy代表的字符,例如:\x0a代表换行
3.type()函数输出变量类型
如:name=‘李明’
print(type(name))
输出:<class ‘str’>
4.常用类型转换:在Python中,字符串、整型、浮点型数据之间的转换非常方便,只需要调用str()、int()、float()这三个函数就能实现。但需要注意:字符串类型的字符必须全部是数字才能被转换为整型和浮点型。
2.1.2运算符
- 赋值运算符:就是=号,将等号右边赋值给左边,如:a=1,a,b=1,a,b=1,2,a=b=c=1
- 算术运算符:主要用于计算,例如+:加,两个数相加;-:减,得到负数或是一个数减去另一个数;*:乘,两个数相乘或是返回一个被重复若干次的字符串;/:除,包括小数点;%:取模,返回除法的余数;**:幂,返回x的y次幂;//:取整除,返回商的整数部分
- 比较运算符:比较运算符是比较2个数,其返回结果只能是布尔值True或False
==,!=,>,<,>=,<=用法和Java一样。注意:==和!=支持所有数据类型的比较,包括数值类型,布尔类型等
- 逻辑运算符:对两个布尔类型操作数进行运算,其结果也是布尔值
and与、并且,和Java的&&一个意思,Python使用and;or或者,与Java中||一个意思,not非,与Java中的!一个意思
- 成员运算符:成员运算符用来判断指定的序列中是否包含某个值,如果包含,返回True,否则返回False
in:如果在指定的序列中找到该值,则返回True;否则返回False如:x in y 如果x在y序列中,返回True; not in如果在指定的序列中没有找到该值,则返回True;否则返回False 如:x not in y:如果x不在y序列中,返回True 注意:y只能是可迭代对象,如字符串,列表,元组,集合,字典等,当y为非迭代对象时,使用成员运算符进行运算将会报错,如print(1 in 12)
- 身份运算符:用于比较两个对象的存储地址
is:判断两个标识符是不是引用自一个对象。如果是则返回True,否则返回False 如:x is y,等价于id(x)==id(y).如果x和y引用同一个对象或者保存在同一块内存地址,返回True,否则返回False is not:判断两个标识是不是引用自一个对象,如果是返回False,否则返回True 如:x is not y,等价于id(x)!=id(y),如果x 和y引用同一个对象或者保存在同一块内存地址,返回False,否则返回True 注意:id()函数返回的是对象指向内存的地址,是一串阿拉伯数字,经常被用来判断对象是否相同 is与==的区别在于is用来判断两个变量引用对象是否为同一个,而==用于判断引用变量的值是否相等。
2.2.1字符串拼接
- 使用运算符拼接字符串:+号,用法和Java一样,Python还有一种特有的方法就是
变量/字符串 * 正整数 说明:输出的是变量所代表的字符串或者字符串本身的正整数倍 如:a='hello' print(a*4),会打印出4个hello的字符串
- 通过占位符格式化字符串:Python支持格式化输出字符串。Python中的字符串可以通过占位符格式化,占位符对应着所要占位的变量类型,并通过“%”给对应占位符传入数值,最终字符串将与占位符传入的值进行拼接
变量1 = 字符串 变量2=‘xxx%sxxx’%变量1 变量3=整数 变量4=‘xxx%sxxx%d’%(变量1,变量3) 说明:%s表示字符串内的占位符,其中的s表示要传入的值是字符串类型,%变量1表示需要传入的值,即变量1的值将传入到占位符所在的位置。当一个字符串中有多个占位符时,需要在%后加上()将传入的变量按位置放入,%(变量1,变量3)表示将变量1和变量3的值分别传入到对应位置的占位符中,%d表示整数类型占位符 %c:格式化字符以ASCII码 %s:格式化字符串 %d:格式化整数 %u:格式化无符号整数 %o: 格式化无符号八进制数 %x: 格式化无符号十六进制数 %X:格式化无符号十六进制数(大写) %f:格式化浮点数,可指定小数点后精度,如:%.2f表示保留两位小数 %e:用科学计数法格式化浮点数 %E:作用与%e相同,用科学计数法格式化浮点数 %g:%f和%e的简写 %G:%f和%E的简写 %p:用十六进制数格式化变量的地址 常用的是%s.%d,%f
2.2.2常用操作字符串的方法
- 统一英文大小写:lower()函数将所有英文字母小写 upper()函数将所有英文字母大写
- 去除字符串首尾空格:lstrip()函数去除字符串开头的空格,rstrip()函数去除字符串末尾的空格,strip()函数同时去除字符串首尾的空格
- 拆分字符串:使用split()对字符串进行拆分,split()函数接收一个分隔符作为参数,以该分隔符为标志将字符串分割为几部分,并将分割部分存入列表中,最后返回整个列表
- 查找字串的位置若要查找某个字符或者某一串字符串是否在字符串中,可以使用内建函数find()来实现,find()函数接收一个字符串作为参数,如果该字符串存在于目标字符串中,则会返回该字符串在目标字符串中的初始索引位置;如果不存在于目标字符串中,会返回-1
- 截取字符串:在Python中,字符串属于可迭代对象,可以直接对字符串使用循环和索引,截取字符串时可以直接使用索引的方式
语法: 字符串变量[索引] 字符串变量[起始索引:结尾索引]索引只能是整数,字符串变量[4]表示取字符串变量中的第4个元素。取一段字符串可以在索引位置中间添加“:”,如字符串变量[6:8]表示从第6个元素开始,到第8个元素结束,但是不包括第8个元素
- 字符串替换:若要对字符串中的某些字符或子串做替换修改可以使用内建函数replace()
语法:字符串变量.replace(要替换的字符串,替换后的字符串)
- 获取字符串的长度:若要知道字符串的长度可以使用内建函数len(),函数len()接收一个可迭代的对象作为参数,返回该对象中元素的个数
3.1.2Python语句块规范
Python使用缩进来区分代码块,缩进可以用2个空格、4个空格或1个tab来实现,但是不能够混用,开发中,一般是统一使用tab键来实现代码的缩进
3.1.3选择结构
1.if控制语句:有单分支,双分支和多分支结构
1. 使用if语句实现单分支结构:语法:if 表达式:
语句块 注意:表达式后要使用冒号:来表示满足此条件要执行的语句块,语句块要缩进
2. 使用if-else语句实现双分支结构
if 表达式:
语句块1
else:
语句块2
3. 使用多分支if语句实现多分支结构
if 表达式:
语句块1
elif 表达式2:
语句块2
else:
语句块3
2.嵌套if控制语句:在if控制语句中又包含一个或多个if控制语句称为嵌套if控制语句
语法: if 表达式1:
if 表达式2:
语句块1
else:
语句块2
else:
if 表达式3:
语句块3
else:
语句块4
3.pass占位语句:由于Python使用缩进来区分代码块,所以代码中不允许有空代码块存在。但在实际开发中,好的开发习惯往往是先确定流程控制语句的结构再将代码填充到代码块中,此时就需要使用pass占位语句来确定控制语句结构而不至于引起集成开发环境报错。pass语句没有任何的执行效果,仅起到占位符的作用
3.2.1循环结构
- while循环
语法: 变量初始化
while 循环条件:
循环体
2 .for循环:用来遍历数据集合或迭代器中的元素,如一个列表或一个字符串
语法: for 循环变量 in 序列表达式:
循环体
- range函数:使用一个for循环遍历一个自增的序列时需要结合range()函数来实现,range()函数能够快速构造一个等差序列。range(start,stop)函数会生成一个左闭右开的数值区间[start,stop),序列中相邻两个整数是差为1如:生成一个0~4的整数序列方法是range(0,5),当起始数值从0开始时,也可以使用range(5)来生成
- 多重循环:多重循环是在循环语句的循环体中又出现循环语句
语法: while 循环条件1:
循环语句1
for 循环变量 in 序列表达式:
循环语句2
3.2.2循环跳转语句
- break语句:在循环中的作用是终止当前循环,然后执行后面的循环,在多重循环,如果内循环使用了break语句,只会终止内层循环语句,不会终止外层循环语句
- continue语句:强制一个循环提前返回,也就是让循环跳出本次循环剩余代码,然后开始下一次循环
4.1.1常用数据结构
- 列表(list):列表是最常用的Python数据结构,数据在列表中是有序的可以通过索引访问列表中的数据。列表中的数据可以修改
- 元组(tuple):元组与列表一样,保存在其中的数据也是有序的,可以通过索引访问元组的数据。元组的数据不能修改。
- 字典(dict):字典中的数据以键值对的形式保存,字典中的键是不重复的唯一的,通过键能够快速地获取对应的值。字典中的数据是无序的。
- 集合(set):集合中的数据是不重复的、无序的。
4.1.2列表(list)
- 列表:用来存储多个数据的数据结构
1.列表中的数据是有序的,每个数据都会分配一个数字来标识这个数据在列表中的位置,称为索引。第一个元素的索引是0,是一个升序整数数列
2.列表的大小和列表中的元素都是可变的
3.列表中可以存储不同数据类型的数据
- 使用列表存取数据
1.创建列表
语法:变量=[数据1,数据2,...]
2.使用索引访问列表数据:列表中的数据是有序的,每个数据都有一个整数索引。列表索引有两种变现形式
(1)正向索引:列表中第一个数据的索引值为0,最后一个数据的索引值为列表长度减1
(2)反向索引:最后一个数据的索引值为-1,第一个数据的索引值为负的列表长度,
也就是说,列表中的每个元素同时具有两个索引:一个正数索引,一个负数索引,无论哪一种索引都能够正确地访问到该元素
语法:
变量 = 列表[索引]
(3)更新列表中的值:列表允许对其中的数据进行添加、删除、修改等操作
append(obj):在列表末尾添加新的数据obj
insert(index,obj):在列表中索引为index的位置插入新的数据obj,插入位置之后的数据索引全部自增1
pop(index=-1):移除列表中的一个元素(默认是最后一个元素),并且返回该元素的值
list[index]=obj:将obj赋值给列表中索引为index的元素
del list[index]:删除列表中索引为index的元素,删除位置之后的数据索引全部自减1
(4)遍历列表:结合循环使用;如果要在遍历列表的过程中修改列表中的元素获取当前元素在列表中索引值,可以先使用len()获取列表长度,再使用range()生成遍历的索引数列,最后在for循环中通过索引访问或修改列表中的元素
4.1.3二维列表:列表中的元素还可以是另一个列表,这种列表称为多维列表。只有一层嵌套的多维列表称为二维列表
语法:
变量=[[元素1,元素2...],[元素1,元素2...],...]
4.1.4元组(tuple)
- 元组:
(1)元组中存储的数据是有序的,每个元素都可以使用索引进行访问,索引规则与列表一致 (2)元组的大小和元组中的元素都是只读的、不可变的(3)元组中可以存储不同数据类型的数据
- 创建元组
语法:
变量 = (数据1,数据2,...)
如果在开发中需要对元组中的数据进行修改,可以将元组转化成一个列表,然后修改列表的数据。将元组转化成列表使用list(),将列表转化成元组使用tuple()
4.2.1字典(dict)
- 字典介绍:如果要保存的数据具备某些唯一性,比如每个人都有一个唯一的身份证号,就可以使用字典来保存这样的数据,以达到通过唯一标识快速获取数据的目的。
字典是一种以键值对(key:value)的形式保存数据的数据结构。具有如下特点
1.键必须是唯一的,但值可以是不唯一的
2.键的类型只能是字符串、数字或者元组,值可以是任意数据类型
3.通过键可以快速地获取与其唯一对应的值
4.字典中的数据保存是无序的
5.字典中的数据的可变的
- 使用字典存取数据
1. 创建字典
语法:变量={键1:值1,键2:值2,...}
2. 访问字典数据:字典中的数据是通过键来访问的
语法:变量=字典[键]
从字典中获取数据时,如果键不存在,从字典中获取就会发生错误。为了避免出现这样的错误,可以先使用in关键字判断键是否存在于字典当中,如果存在,再从字典中取值
3. 更新字典中的数据:向字典中添加数据和修改数据的语法相同
语法:字典[键]=值
说明:如果键不存在于字典中,就向字典中添加新的键和值,如果键已经存在于字典中,就将新值赋给键对应的值
4. 删除字典中的数据:字典中的数据也可以删除,删除字典中的值是通过键来完成的
语法:del 字典[键]
注意:在既需要保存的数据有序,又需要快速获取数据的信息时,可以将列表与字典搭配起来使用
4.2.2集合(set)
5. 集合:集合是用来存储多个数据的数据结构,它与列表很像,但与列表的使用场景和具备的特性有很大区别
1. 集合中保存的数据是唯一的,不重复的。向集合中添加重复数据后,集合只会保留一个
2. 集合中保存的数据是无序的
- 使用集合存取数据
1. 创建集合:分为两种
(1)创建一个空集合
语法: 变量=set()
(2)创建一分非空集合
语法: 变量={元素1,元素2,...}
2. 使用集合结构:可以向一个已经存在的集合中添加或删除元素,添加元素使用add(),删除元素使用remove()
3. 集合运算:Python中的集合运算与数学上的集合一样,也可以计算两个集合的交集和并集
语法:|:计算两个集合的并集
&:计算两个集合的交集
5.1.1无参函数
- 函数的概念:函数是一种组织好的、允许重复使用的代码段。通常函数都用来实现单一或相关联的功能。
语法:
def 函数名(参数列表):
函数体
[return 函数返回值]
- 无参函数:参数列表为空的函数
5.1.2有参函数
函数的参数在定义时可分为:
1. 位置参数
2. 默认参数
3. 包裹位置参数
4. 包裹关键字参数
其中,包裹位置参数和包裹关键字参数都属于可变参数
在调用函数时,有一种特殊的给函数参数传值的方法:使用参数的名字作为关键字来给参数传值,这种参数被称为关键字参数
- 位置参数:是最基本的函数参数
语法:def 函数名(arg1,arg2,arg3):
函数体
- 默认参数:在定义函数是给参数设置默认值,设置默认值的参数,在调用时可以不给这个参数显示赋值,此时参数值就是它的默认值,调用时如果给默认值赋值,则该默认值不生效。
语法:def 函数名(start,end=12):
函数体
注意:在给函数的参数设置默认值时,设置默认值的参数要定义在普通的位置参数后面,否则解析器会报错
- 不定长参数:分为两种,包裹位置参数和包裹关键字参数
1. 包裹位置参数:在函数中使用包裹位置参数,将允许函数接收不定长个位置参数,这些参数将会被组织成一个元组传入函数中
语法:def 函数名(*args):
函数体
2. 包裹关键字参数:和包裹位置参数一样都是可变参数,只是接收的参数都是以关键字参数的形式传入的,参数名=参数值,当参数传入到函数中后,这些参数将会以字典的形式组织在一起,其中关键字参数的参数名就是字典中的键,参数值就是键对应的值
语法:def 函数名(**kwargs):
函数体
注意:在定义有参函数时,不同类型参数的定义要按以下顺序,以免引起错误:
def 函数名(位置参数,包裹位置参数,默认参数,包裹关键字参数)
5.1.3函数的返回值
- return关键字:返回的数值可以是任意类型,当然,return关键字后面也可以没有任何数值,表示终止函数的执行。
语法: def 函数名(参数列表): 函数体 [return [函数返回值]]
- yield关键字:也在函数中用于返回数值,和return的区别如下:
使用yield作为返回关键字的函数叫作生成器。生成器是一个可迭代对象,在Python中能够使用for...in...来操作的对象都是可迭代对象,如之前学过的列表和字符串就是可迭代对象。使用yield返回值的函数也可以使用for..in..来操作。但是生成器每次只读取一次,也就是使用for循环迭代生成器的时候,每次执行到yield语句,生成器就会返回一个值,然后当for循环继续执行时,再返回下一个值。yield像一个不终止函数执行的return语句。每次执行到它都会返回一个数值,然后暂停函数(而不是终止),直到下一下从生成器中取值。
5.2.1模块:Python中使用模块来管理代码,事实上一个Python文件(一个以.py结尾的文件)就是一个模块。在模块中可以定义函数、类和变量,甚至可以包含可执行代码。
- 导入模块:Python的模块分为内置模块和第三方模块。当在自己的代码文件夹中调用其他模块的代码时,首先要确保该模块已经安装,然后使用import关键字导入模块。
语法:from 模块名 import 方法名或类名 还可以给模块取一个别名: 语法:import 模块名 as 模块的别名 可以给模块中的方法或类取别名 语法:from 模块名 import 模块中的方法或类 as 别名 注意:假如导入的模块使用了as 起了别名,那么原名就不能使用了,只能使用别名进行调用
- 创建模块:Python中,一个.py文件就是一个模块,文件名就是模块名字。如果调用者和被调用者处于同一个文件夹下,使用关键字import加文件名即可导入模块。
其他文件夹下的文件导入包中模块时的语法: import 包名.模块名
5.2.2 常用模块
- 内置模块介绍:安装Python后就可以直接使用的模块,通常是一些使用场景广泛的模块
```python
常用内置模块:
time : 用于获取时间戳或进行时间格式的转换
datetime :包含方便的时间计算方法
random :用于生成随机数
os :提供对操作系统进行调用的接口
shutil: 高级的文件、文件夹、压缩包处理模块
```
- 第三方模块:更具有针对性,用于处理更专业的问题。
```python
numpy : 数据分析领域的常用库,用于矩阵和向量运算
pandas : 数据分析领域的常用库,提供了非常多的统计计算方法
matplotlib :优秀的2D绘图库,常用于数据分析领域的绘图绘制
scipy :科学计算库,包含了大量的科学计算方法
sklearn : 继承了非常多的机器学习模型的库
scrapy : 优秀的爬虫框架,可以快速地完成爬虫的开发
```
7.1.1异常概述
- 认识异常:异常是在程序运行中发生的非正常事件,这类事件可能是程序本身的设计错误,也可能是外界环境发生了变化,如网络连接不通、算术运算出错、遍历列表超出范围、导入模块不存在等,程序会中断正在运行的程序
- 常见的异常:
(1)NameError:当程序访问一个未声明的变量或者函数时,会引发NameError异常 (2)ZeroDivisionError:在计算的过程中,当有除数为0的情况发生时,会引发ZeroDivisionError异常。 (3)SyntaxError:当程序出现语法错误时,会引发SyntaxError异常 (4)IndexError:当使用程序中不存在的索引时,会引发IndexError异常 (5)KeyError:当使用字典中不存在的键时,会引发KeyError异常
7.1.2异常处理
-
异常处理:异常处理就像人们平时对可能遇到的意外情况,预先想好了一些处理方法。和Java异常处理的原理是一样的。
-
使用try-except处理异常:进行异常的捕获和处理,把可能出现异常的代码放入try语句块中,并使用except语句块来处理异常。
语法: try: ...#语句块1 #尝试运行语句块1 except ErrorName1: ...#语句块2 #如果语句块1触发ErrorName1这种异常,运行语句块2 except ErrorName2 as e: ...#语句块3,例如:print(e) #如果语句块2没运行,且语句块1触发了ErrorName2这种异常,运行语句块3 ...#except ErrorName 这个语句可以有多个。类似于elif except: ...#语句块4 #当代码1出现异常,但不是ErrorName1和ErrorName2的其他异常,运行代码块4 else: ...#语句块5 #如果语句块1运行正常,则运行语句块5,否则不运行 主要关键字:try:执行可能会出现错误的试探性语句,即这里的语句可能导致致命性错误,是程序无法继续执行下去。 except:如果在try语句块中无法正确执行,那么久执行except语句块里面的语句,这里可以是打印错误信息或者其他的可执行语句。 else:如果try语句块可以正常运行,那么执行else里面的语句。 注意:(1)如果try语句块在执行过程中某一句代码发生异常,try语句块中该句代码之后的代码都将被忽略 (2)当有多个except ErrorName语句块时,捕获异常的范围需要遵循先小后大的规则,
-
使用try-except-finally进行异常处理
语法: try: ...#语句块1 #尝试运行语句块1 except: ...#语句块2 #如果语句块1发生异常,语句块2运行 ...#中间可以有多个except ErrorName finally: ...#语句块3 #先不管语句块1或2运行,语句块3都运行
-
使用raise跑出异常:主动抛出异常
语法: raise ErrorName #抛出ErrorName的异常 raise ErrorName()#抛出ErrorName的异常 raise #重新引发刚刚发生的异常 还可以自定义描述信息 print('raise 语句演示') raise IndexError(‘仔细观察一下,是否索引引用出界了’)
7.2.2利用PyCharm进行debug
-
设置断点
1.通过鼠标左键单击PyCharm编辑区域中序号和代码内容中间的区域可以设置断点 2.可以设置多个断点,程序会按照代码执行的顺序进入断点。上一个断点检查完,可以手动让程序继续执行,到达下一个断点处程序又将进入断点 3.在项目代码较多时,如果想要选择性地让某一些断点允许程序进入,而另一些断点希望程序暂时忽略,可以在断点位置单击鼠标右键,将Suspend选项取消勾选即可
-
进入调试模式界面
(1)查看变量信息:通过Variables模块中的信息,可以查看程序进入断点时所有的变量信息,包括变量当前的值或内容、变量的类型等 (2)常用快捷键 F7:step into 进入,按顺序逐步停止,如果遇到函数,会进入到函数内,并在调试界面中显示运行该行代码后得到的变量信息 F8:step over 单步 如果断点设置在一行执行代码处,效果会和F7键一样;如果断点设置在函数调用的代码上,F8键将会忽略,不进入函数,直接外跳到下一行 F9:resume program 运行到下一个断点处,适合快速调试 shift+F8组合键,跳出函数,当进入函数内,可以使用Shift+F8组合键:跳出函数。
8.1.1面向对象的编程思想:三大特性:封装、继承和多态
8.1.2类和对象
-
使用类创建实例对象
语法: class ClassName(): 定义类的属性和方法 class关键字后面的ClassName是类名,类的命名方法通常使用单词首字母大写的驼峰命名法。类名后面是一个(),表示类的继承关系,可以不填写,表示默认继承object类,括号后面接“:”号表示换行,并在新的一行缩进定义类的属性或方法。当然,也可以定义一个没有属性和方法的类,这需要用到之前学过的pass关键字 创建好类之后就可以使用这个类来创建实例对象了 语法: 变量 = 类名()
-
给类添加实例方法:在类中定义方法与定义函数非常类似,实际上方法和函数起到的功能也是一样的,不同之处是一个定义在类外,一个定义在类内。定义在类外的称为函数,定义在类内的称为类的方法。实例方法是只有在使用类创建了实例对象之后才能调用的方法,即实例方法不能通过类名直接调用
语法: def 方法名(self,方法参数列表): 方法体 #注意:第一个参数必须是self,这里的self代表的含义不是类,而是实例,也就是通过类创建实例对象后对自身的引用。self非常重要,在对象内只有通过self才能调用其他的实例变量或方法。
-
构造方法和析构方法
在类中有两个非常特殊的方法:_init_()和_del_() _init_()方法会在创建实例对象的时候自动调用(初始化),_del_()方法会在实例对象被销毁的时候自动调用。因此_init_()被称为构造方法,_del_()被 称为析构方法 这两个方法即便在类中没有显式地定义,实际上也是存在的。在开发中,也可以在类中显式地定义构造方法和析构方法。这样就可以在创建对象的时,在构造方法里添加上代码完成对象的初始化工作;在对象销毁时,在析构方法里添加一些代码释放对象占用的资源。 注意:del 实例的对象 #销毁对象的意思
-
类的变量:对象的属性是以变量的形式存在的,在类中可以定义的变量类型分为实例变量和类变量两种
(1)实例变量:最常用的变量类型 语法:self.变量名 = 值 通常情况下,实例变量定义在构造方法中,这样实例对象被创建时,实例变量就会被定义,赋值,因而可以在类的任意方法中使用。 在Python中的变量不支持只声明不赋值,所以在定义类的变量时必须给变量赋初始值。常用数据类型初值: 数值类型 value=0 字符串 value=“” 列表 value=[] 字典 value={} 元组 value=() 通过给构造方法添加参数的方式,就能够在创建对象时完成初始化操作。对象的方法和函数一样也支持位置参数、默认参数和不定长参数。 在类外给实例对象动态添加实例变量,不使用self,而是使用“实例对象.实例变量名”的方式。这种添加方式是动态的,只针对当前实例对象有效,对其他实例对象不会有任何影响。 (2)类变量 实例变量是必须在创建实例对象之后才能使用的变量。在某些场景下,希望通过类名直接调用类中的变量或者希望所有类能够公有某个变量。这个情况下,就可以使用类变量。类变量相当于类的一个全局变量,只要是能够使用这个类的地方都能够访问或者修改类变量的值。类变量和实例变量不同,不需要创建实例对象就可以使用。 语法: class 类名(): #定义类变量 变量名 = 初始值
8.2.1继承
-
继承:新类可以在不增加代码的条件下,通过从已有的类中继承其属性和方法来充实自身,这种现象或行为就称为继承。此时,新的类称为子类,被继承的类称为父类。继承最基本的作用就是使代码得以重用,并且增加了软件的可扩展性
所有的类都默认继承自object 语法:class 子类类名(父类类名): #定义子类的变量和方法 #子类继承父类后就拥有父类的属性和方法,如果子类没有定义__init__()方法,就会自动继承父类的__init__()方法;如果子类中定义了自己的构造方法,那么父类的构造方法就不会被自动调用 在子类中调用父类的构造方法,实现的方式是使用super()显示调用父类的构造方法 #柜员类 class BankTeller(BankEmploee): def __init__(self,name="",emp_num="",salary=0): super().__init__(name.emp_num,salary)
-
子类的变量和方法:子类能够继承父类的变量和方法,作为父类的扩展,子类中还可以定义属于自己的变量和方法。
-
封装:封装一个是隐藏属性、方法与方法实现细节的过程,在使用面向对象的编程时,会希望类中的变量或方法只能在当前类中调用。对于这样的需求可以采用将变量或方法设置成私有的方式实现。
语法: 私有变量:__变量名 私有方法:__方法名() 设置私有变量或私有方法就是在变量名或方法名前加上“__”(2个下划线)设置私有的目的:一是保护类里的变量,避免外界对其随意赋值;二是保护类内部的方法,不允许从外部调用 class BankEmployee(): def __init__(self,name="",emp_num="",salary=0): self.__name=name self.__emp_num=emp_num self.__salary=salary #如:set方法 def set_name(self,name): self.__name=name #get方法 def get_name(self,name): return self.__name 在类中还存在方法名前后都有“__”的方法,这些方法不是私有的方法,而是表明这些方法是Python内部定义的方法。开发人员在自定义方法时一定不能在自己的方法名前后都加上“__”
-
多继承:继承能够解决代码重用的问题,但是有些情况下只继承一个父类仍然无法解决所有的应用场景。Python语句使用多继承来解决这样的问题,一个类只有一个父类的情况称为单继承
语法: class 子类类名(父类1,父类2): #定义子类的变量和方法 注意:如果子类继承了多个父类且没有自己的构造方法,则子类会按照继承列表父类的顺序,找到第一个定义了构造方法的父类,并继承它的构造方法。
8.2.2多态
1. 多态介绍:面向对象三大特性:继承、封装、多态;多态:一个变量可以引用不同类型的对象,并且能自动地调用被引用对象的方法,从而根据不同的对象类型,响应不同的操作。继承和方法重写是实现多态的技术基础。
2. 方法重写:当子类从父类中继承的方法不能满足子类的需要时,在子类中对父类的同名方法进行重写(覆盖),以符合需求。
3. 实现多态:优势
(1)可替换性:多态对已存在的代码具有可替代性。
(2)可扩充性:多态对代码具有可以扩充性。增加新的子类并不影响已存在类的多态性和继承性,以及其他特性的运行和操作。实际上新增子类更容易获得多态功能。
(3)接口性:多态是父类向子类提供的一个共同接口,由子类来具体实现。
(4)灵活性:多态在应用中体现了灵活多样的操作,提供了使用效率。
(5)简化性:多态简化了应用软件的代码编写和修改过程,尤其是在处理大量对象的运算和操作时,这个特点尤为突出和重要。
9.1.1认识最常用的文件类型
-
文件:文件是存储在某种存储设备或临时存储设备中的一段数据,并且归属于计算机文件系统的管理之下。所谓“长期存储设备”,一般指磁盘、光盘、磁带等。简而言之,文件是存储在存储媒介上的信息或数据,信息或数据可以是文字、照片、视频、音频等。
-
常见的数据分析文件类型和扩展名
(1)文件扩展名:.csv 描述:csv全称是comma-separated values,即逗号分隔的值,经常用来作为不同程序之间数据交互的格式。解析之后与数据库表格式很类似,是数据分析最常用的数据类型之一 Python库:csv 方法解析:pandas.read_csv() (2)文件扩展名:.json 描述:json格式用于网络上传输结构化数据。json格式的文件可以很容易使用任何编程语言来读取,在Python中,它是一种类似列表和字典的多维嵌套的形式 Python库:json 方法解析:pandas.read_json() (3)扩展名:.xlsx 描述:xlsx是微软Excel打开的xml文件格式,也是电子表格文件格式。xlsx数据是在一个表的单元格和列下组织的,每个xlsx文件可以包含多于一个的表格,即工作簿可以包含多个表 方法解析:pandas.read_excel() (4)扩展名:.zip 描述:zip格式是存档文件格式,也是常说的压缩文件格式。通常数据分析会将大量数据进行压缩 Python库:zipfile (5)扩展名: .txt 描述:txt是纯文本格式 方法解析:open() (6)扩展名:.xml 描述:xml也称为可扩展标记语言,具有一定的编码数据规则,是一个人类和机器均可读的文件格式 Python库:xml
9.1.2txt文件读写操作
1. 利用open、close方法打开、关闭文件:在Python中进行文件的打开和关闭操作使用两个内置方法:open方法和close方法。
open方法主要参数:
path:必须(参数),表示文件路径(可以绝对路径,也可相对路径)
mode:不是必须,默认‘r’ 打开模式
encoding: 不是必须,默认None 编码格式
例如:
news = open(‘news.txt’) #打开news.txt文件,参数为相对路径
print(news)
news.close()
news = open(‘D:\pycharm\news.txt’) #参数为绝对路径
print(news)
news.close()
2. read、write读写文件
(1)文件打开模式:使用open方法打开news.txt文件时,有一个参数mode,表示文件打开模式,最常用的有w(只写)模式,r(只读)、a(只追加)模式,默认为只读模式
通过r(只读)模式打开文件,只能使用read方法读取文件内容,而不能使用write方法对内容进行修改。
通过w(只写)模式或a(只追加)模式打开文件,只能使用write方法将内容写入文件中,而不能使用read方法读取文件内容。w模式和a模式的区别是:w模式是从文件光标所在处写入内容,如果原文件中有内容,则新写入内容会覆盖之前的内容;a模式是从文件末尾处追加内容,不会覆盖原有内容。
在打开模式中,也有既可以写也可以读的打开方式,例如r+、w+等。
打开模式:r
描述:以只读方式打开文件。文件的指针将会放在文件的开头。这是默认模式
打开方式:rb
描述:以二进制格式打开文件,用于只读。文件指针将会放在文件的开头
打开方式:r+
描述:打开文件用于读写。文件指针将会放在文件的开头
打开方式:rb+
描述:以二进制格式打开文件,用于读写。文件指针将会放在文件的开头
打开方式:w
描述:打开文件用于写入。如果该文件已存在,则打开文件,并从头开始编辑,即原有内容会被删除;如果该文件不存在,创建新文件。
打开模式:wb
描述:以二进制打开文件,用于写入。如果该文件已存在,则打开文件,并从头开始编辑,即原有内容会被删除;如果该文件不存在,创建新文件
打开模式:w+
描述:打开文件用于读写。如果文件已存在,则打开文件,并从头开始编辑,即原有内容会被删除;如果该文件不存在,创建新文件
打开模式:wb+
描述:以二进制格式打开文件,用于读写。如果该文件已存在,则打开文件,并从头开始编辑,即原有内容会被删除;如果该文件不存在,创建新文件
打开模式:a
描述:打开文件用于追加。如果该文件已存在,文件指针将会放在文件的结尾,也就是新的内容将会写入到已有内容之后;如果该文件不存在,创建新文件进行写入
打开模式:ab
描述:以二进制格式打开文件,用于追加。如果该文件已存在,文件指针将会放在文件的结尾,也就是新的内容将会写入到已有内容之后;如果该文件不存在,创建新文件进行写入
打开模式:a+
描述:打开文件用于读写。如果该文件已存在,文件指针将会放在文件的结尾,文件打开时使用追加模式;如果该文件不存在,创建新文件用于读写
打开模式:ab+
描述:以二进制格式打开文件,用于追加。如果该文件已存在,文件指针将会放在文件的结尾,如果该文件不存在,创建新文件用于读写
read方法是读取整个文件的内容并返回,返回类型是str;write方法是写入方法,接收str类型的数据作为参数,将内容写入已经用可写模式打开的文件中
如:在news.txt空文件中,写入新闻稿内容“北京市明天傍晚有雨”
实现步骤:(1)打开news.txt文件,将打开模式设为w(可写)模式
(2)使用write方法将内容写入
(3)调用close方法将文件关闭
file=open(‘news.txt’,mode='w')#通过w模式打开news.txt文件
file.write('北京市明天傍晚有雨') #写入内容
file.close() #关闭文件
通过只读模式打开news.txt文件
file=open(‘news.txt’,mode='r')#通过r模式打开news.txt文件
print(file.read()) #查看内容
file.close() #关闭文件
使用a追加模式打开并追加标题
file=open(‘news.txt’,mode='a')
file.write('\r作者:张三') #先换行再输入,插入一个换行符
file.close()
2.文件读写位置:在记事本编辑txt文件时,都会有一个光标,表示目前需要在哪个位置进行编辑。在Python文件的读写过程中,也提供一种类似的方法seek来定位文件的读写位置。seek接受两个参数,第一个参数是偏移量,表示光标移动几个字符,第二个参数是定位,0表示从文件开头开始,1表示从当前位置开始,2表示从文末开始,默认是0
file=open(‘news.txt’,mode=‘r+’)#r+为即可读也可写模式
content = file。read() #记录下之前文章的内容,并将光标移动到内容的末尾
file.seek(0,0)#移动光标到最前头
file.write(‘标题:北京市天气预报\r’+content)#写入内容
file.close()
注意:file.read()方法不仅仅的读取内容,同时会将光标移动到内容的末尾,而file.write()方法是从光标处写入内容,并具有覆盖的特点。所以在使用file.write()方法之前需要先将原有内容记录下来,并将光标移动到内容最开头,才能顺利完成任务要求。
3.文件编码格式
(1)ASCII码,ASCII码使用1个字节存储英文和字符,主要是英文等欧洲国家的语言符号
(2)Unicode,使用2个字节来存储大约65535个字符,包括除英文外很多其他国家的语言符号。
(3)UTF-8,是Unicode的实现方式之一,对中文友好。
GBK,汉字内码扩展规范,将汉字对应成一个数字编码。
例如:
file = open('news.txt',mode='r',encoding='ascii')
print(file.read())
file.close()
3.行读取文件:即将每一行当成一个单位字符串,或逐行返回或整体返回。
行读取有两种方法:readline和readlines。readline方法只读取文件的下一行,返回类型为str,当遇到比较大的文件的时候,可以用这种方法来避免内存不足问题;readlines方法读取文件的所有行,可以用循环遍历的方式逐行读取,返回类型是list
例如:使用行读取的两种方法分别读取文件news.txt
实现步骤:
(1)打开news.txt文件
(2)将打开模式设为r(可读)模式
(3)使用while循环,利用readline方法按行读取,直到没有下一行为止
(4)使用readlines方法读取文稿,然后使用for循环遍历打印
file = open(‘news.txt’,mode=‘r’)
line = file.readline()
while line:
print(line)
line=file.readline()
for line in file.readlines():
print('readlines方法:'+line)
9.1.3with语句
描述:在绝大对数情况下,在打开文件并操作完之后,是需要将文件关闭的,这样既能避免文件IO的冲突,也能节约内存的使用。但是每次打开关闭会比较麻烦,Python提供了with语句来解决这个问题。在with语句下对文件操作,可以不用执行close方法关闭,with语句会自动关闭
```python
with主要作用:
(1)解决异常退出时的资源释放问题
(2)解决用户忘记调用close方法而产生的资源泄露问题
语法:
with open(...) as name:
name.read()
......
其中,name是给这个打开的文件取的名字,不能与其他变量或者关键字冲突
例如:使用with语句打开news.txt文件
with open(‘news.txt‘)as file:
print(file.read())
print(file.read())
由此可见最后的print()读取时报I/O operation on closed file. 说明打开的文件已经关闭了
```
9.2.1csv与json读写
-
进一步了解csv和json格式
要在Python中操作或处理这两种格式的文件,需要用到Python的内置模块csv和json
json格式样例:
{“姓名”:“张三”,“成绩”:[{“第一次月考”:“83”},{“期中考试”:“88”},{“期末考试”:“76”}]}
csv格式样例:
姓名,第一次月考成绩,期中考试成绩,期末考试成绩
张三,83,88,76 -
csv模块:在csv模块中,提供了最重要的读写csv文件的方法:reader和write,这两个方法都接受一个可迭代对象作为参数,这个参数可以理解为一个打开的.csv文件。reader方法返回一个生成器,可以通过循环对其整体遍历。writer方法返回一个writer对象,该对象提供writerow方法,将内容按行写入csv文件中
例如: 将.txt文件转换为csv文件 student.txt中的内容如下: 姓名 年龄 成绩 张三 16 85 李四 16 77 韩梅梅 17 93 李雷 17 59 分析: (1)可以看到一共有5行数据,其中第1行为数据列标题,其余4行为具体数据,3个数据列表题分别为:姓名、年龄、成绩。内容用空格分隔开 (2)读取和写入学生数据到csv中,需要使用csv模块。先用之前学过的txt文件处理方式,将文件内容读取,之后再通过csv模块中的方法将数据写入 实现步骤: 《1》打开student.txt文件,按行循环遍历读取内容 《2》打开空的student.csv文件,在步骤《1》遍历的同时,将内容按行写入student.csv文件中。 《3》关闭两个文件 关键代码: import csv #导入csv模块 with open(‘student.csv’,‘w’,encoding='utf-8',newline='') as csvfile: #打开csv文件 writer = csv.writer(csvfile)#创建一个编辑对象 with open(‘student.txt’,‘r’,encoding='utf-8') as f: #打开txt文件 for line in f.readlines(): line_list = line.strip('\n').split('')#将str内容转换为list,去除换行符 writer.writerow(line_list)#将内容按行写入 可以看到,虽然在程序中没有加逗号这个操作,但是文件内容也自动用逗号分隔开了,这就是csv文件的特点---用逗号分隔的文本文件。这种数据格式在数据分析领域非常常见,因为分隔符是简单的逗号,在加载和处理数据的时候都非常方便。 注意:如果调用open方法时没有传入newline=‘’参数,在将内容写入csv文件中时,会有空格行的出现。
-
json模块
描述:在json模块中,最常使用的两个方法是将Python对象编码成json字符串的json.dumps方法和将json字符串解码为Python对象的json.loads方法。要将Python对象编码存放到.json文件中,需要用到json.dump方法;要从.json文件中将内容解析成Python对象,则需要用到json.load方法json.dump:将Python对象编码存入.json文件中 json.dumps:将Python对象编码成json字符串 json.load:将.json文件解析成Python对象 json.loads:将已编码的json字符串解码为Python对象 例如:使用json.dumps方法将data数据编码成json字符串,再使用json.loads方法将json字符串解析成原来的data数据 关键代码: import json data=[{'a':1,'b':2,'c':3}] #构造一个简单字典和列表嵌套的数据 json_data=json.dumps(data)#编码成json字符串 print(json_data) print(type(json_data)) python_obj = json.loads(json_data)#解析成Python对象 print(python_obj) print(type(python_obj)) 例2:将学生数据student.txt文件转换为json格式,然后写入student.json文件中 分析: (1)使用json模块的方法实现 (2)将student.txt文件中的数据写入student.json文件中,先将内容放入Python的数据结构中(字典和列表),之后再将这个Python对象转换并写入json文件中 (3)将这种类似表格的数据转换为json数据,比较好的做法是将student.txt中的每一行数据写入一个字典中,最后将所有字典写入一个列表中 实现步骤: 《1》打开student.txt文件,按行循环遍历内容 《2》将第一行内容(数据列名)当作每个字典的key,将其他行作为字典的value 《3》将所有的字典放在一个列表中 《4》打开student.json文件,利用json.dump方法将该列表进行json编码并放入到文件中。 关键代码: import json with open(‘student.txt’,‘r’,encoding='utf-8') as f: content=[] #建立空列表待用 content_json=[] #建立空列表待用 for line in f.readlines(): line_list=line.strip('\n').split('') content.append(line_list) #将txt文件内容存入列表中 keys = content[0] #将第一行内容取名叫keys,待用 for i in range(1,len(content)): content_dict={}#将其他行内容建立为字典 for k,v in zip(keys,content[i]): content_dict[k]=v #给字典的条目赋值 content_json.append(content_dict) #将所有数据字典放入列表中 print(content_json) with open('student.json',mode='w') as j: json.dump(content_json,j) 可以看出,内容已经全部保存到student.json文件中了,并被自动编码成了Unicode格式,这时要重新将文件中的内容解析为Python的列表,只需要用json.load方法就可以完成。上面使用了zip方法,zip方法接收多个可迭代对象作为参数,然后将对象中对应位置的元素组合成一个个元组,返回由这些元组组成的列表,例如zip(['a','b','c'],['a','b','c'])返回的结果是[('a','a'),('b','b'),('c','c')]
9.2.2 路径和文件的操作
描述:在Python中,能对路径和文件操作的模块很多,下面介绍三种常用的模块:os,glob,shutil
1. os模块
```python
描述:os模块是Python标准库中的一个用于访问操作系统的模块,包含了普遍的操作系统功能,比如复制、创建、修改、删除文件及文件夹,设置用户权限等功能。
os模块常用方法的功能和描述
(1)功能和操作:查看当前使用平台
方法名:os.name
描述:返回当前使用平台的代表字符,Windows用‘nt’表示,Linux用'posix'表示
(2)功能和操作:查看当前路径和文件
方法名:os.getcwd()
描述:返回当前工作目录
方法名:os.listdir(path)
描述:返回path目录下所有文件列表
(3)功能和操作:查看绝对路径
方法名:os.path.abspath(path)
描述:返回path的绝对路径
(4)功能和操作:运行系统命令
方法名:os.system()
描述:运行shell命令
(5)功能和操作:查看文件名或目录
方法名:os.path.split(path)
描述:将path的目录和文件名分开为元组
方法名:os.path.join(path1,path2,...)
描述:将path1,path2,...进行组合,若path2为绝对路径,则会将path1删除
方法名:os.path.dirname(path)
描述:返回path中的目录(文件夹部分),结果不包含‘\’
方法名:os.path.basename(path)
描述:返回path中的文件名
(6)功能和操作:创建目录
方法名:os.mkdir(path)
描述:创建path目录(只能创建一级目录,如“F:\XXX\WWW”),在XXX目录下创建WWW目录
方法名:os.makedirs(path)
描述:创建多级目录(如“F:\XXX\SSS”),在F盘下创建XXX目录,继续在XXX目录下创建SSS目录
(7)功能和操作:删除文件或目录
方法名:os.remove(path)
描述:删除文件(必须是文件)
方法名:os.rmdir(path)
描述:删除path目录(只能删除一级目录,如“”F:\XXX\SSS),只删除SSS目录
方法名:os.removedirs(path)
描述:删除多级目录(如“F:\XXX\SSS”),删除SSS,XXX两级目录
(8)功能和操作:查看文件大小
方法名:os.path.getsize(path)
描述:返回文件的大小,若是目录则返回0
(9)功能操作:查看文件
方法名:os.path.exists(path)
描述:判断path是否存在,存在返回True,不存在返回False
方法名:os.path.isfile(path)
描述:判断path是否为文件,是返回True,不是返回False
方法名:os.path.isdir(path)
描述:判断path是否为目录,是返回True,不是返回False
```
-
glob模块
描述:利用os模块可以完成绝大部分对文件及路径的操作,但有时需要在一个文件夹下查找某个类型的文件,利用os模块会比较难实现。glob模块提供了一个很好用的方法来查找某个类型的文件—glob方法,它接收一个路径作为参数,返回所有匹配到的文件,类型是list,最重要的是glob方法提供模糊匹配的方式,可以查找到自己想要类型的文件。例如,查找路径“D:/”下的所有.json文件,只需要写下语句glob.glob(‘D:/*.json’),就会找到路径“D:/”下的所有json文件
注意:glob.glob方法返回的是list -
shutil模块
描述:shutil模块是对os模块中文件操作的进一步补充,是Python自带的关于文件、文件夹、压缩文件的高层次的操作工具。shutil模块中提供了文件复制的方法copy和文件移动剪切的方法move,它们都接受两个参数,第一个参数是原文件路径,第二个参数是目的文件路径