一.Python语言概述
1.面向对象的解释性程序设计语言
2.自由软件
3.可移植到多平台
4.设计哲学是优雅、清晰、简单
1.1编程方式
1.1.1交互式
在python自带的idle每次只执行一段代码
1.1.2.文件式
在idle中新建一个py文件在文件中编写代码,保存执行后run module
1.2.标识符和变量
在不同的应用环境同的应用环境下,用于识别实体的符号。
标识符由字母、下划线和数字组成,不能从数字开始。不能属于关键字,标识符区分大小写。
1.2.1python的关键字
False | def | if | raise |
---|---|---|---|
None | del | import | return |
True | elif | in | try |
and | else | ls | while |
assert | except | lambda | with |
break | finally | nonlocal | yield |
class | for | not | |
continue | from | or | |
as | global | pass |
1.2.2常量和变量
常量是不能改变的量
比如3.1415926是常量
变量就是值可以改变的量,变量名则是程序为了方便的引用内存中的值而为它取的名称。
Python变量名对大小写敏感
注:不要使用python内置函数被用作变量名,否则内置函数将无法使用。如果要恢复和使用del函数
Python变量有一个非常重要的性质:变量是将名称与对象联系起来
赋值操作不会实际复制值,只是为数据对象取相关名称。
id()是Python可显示对象地址的内置函数
小整数Python将数值放在数组中,以提高效率重新分配内存空间
1.输入函数和输出函数
1.3.1输入函数input()
input函数在python从标准输入(键盘)中读入字符串是一个内建函数。
如果要输入其他数据类型的数据
like a=int(input())
输入多个值,在同一行实现
a,b=input().split()
提示输入时
n=int(input("请输入整形值N:"))
1.3.2输出函数print
语法 print(输出值)默认换行
如果中间有多个值,用逗号隔开
for i in range(5) print(i) //结果换行输出
如果不想换行
for i in range(5) print(i.end='')
例子1 计算三角形面积
import math a=int(input()) b=int(input()) c=int(input()) s=(a b c)/2 area=math.sqrt(s*(s-a)*(s-b)*(s-c)) print("三角形边长:",a,b,c,end=' ') print("三角形的面积:",area)
例子2 绘画五角星
import turtle turtle.forward(200) turtle.right(144) turtle.forward(200) turtle.right(144) turtle.forward(200) turtle.right(144) turtle.forward(200) turtle.right(144) turtle.forward(200) turtle.done()
二.用Python语言编写程序
2.1 数字类型
整数(int)值的范围一般是无限的
进制 | 前导符 | 示例 | 十进制 |
---|---|---|---|
二进制 | 0b或0B | 0b10 | 2 |
八进制 | 0o或0O | 0o10 | 8 |
十六进制 | 0x或0X | 0x10 | 16 |
浮点数(float)
值的范围和精度有限
表示方式
1.23*10^9 1.23e9
浮点数运算存在的问题
浮点数运算尾数不确定,存在误差
采用round尾数消除函数
复数(complex)
由实部和虚部组成,虚部用j表示
例如
2 3j
表示方法
算术运算符
运算符 | 说明 | 示例 | 运算结果 |
---|---|---|---|
加法 | 5 10 | 15 | |
- | 减法 | 100-5 | 95 |
* | 乘法 | 8*9 | 72 |
/ | 浮点数除法 | 100/5 | 20.0 |
// | 整数除法 | 100//5 | 20 |
% | 模(求余) | 9%4 | 1 |
** | 幂 | 2**3 | 8 |
整数除法向左取整(即向数轴左取整)
数学库(math)
函数或常数 | 功能 | |
---|---|---|
e | 自然常数 | |
pi | 圆周率 | |
log(x,[base]) | 返回以base为底的对数,缺省为e | |
pow(x,y) | 返回x的y次方 | |
sqrt(x) | 返回x的平方根 | |
fabs(x) | 返回x的绝对值 | |
round(x[,n]) | 返回浮点数x的四舍五入值,n代表舍入到小数点后的位置 | |
divmod(x,y) | 返回x和y的商和余数 |
2.2 字符串
字符串是以引号括起来的任意文本,是一个有序序列
单引号双引号表示单行文本,三引号表示多行文本
转义字符
\ | *在字符串行尾,即一行未完,转到下一行继续写 |
字符串运算符
运算符 | 功能 | 示例 |
---|---|---|
+ | 连接字符串 | ‘hello’+‘world’ ‘helloworld’ |
* | 复制字符串 | ‘ab’*3 ‘ababab’ |
字符串切片
字符串是一个有序序列,可以是正向递增也可以是反向递减:
0 | 1 | 2 | 3 | 4 | 5 | 6 | 7 |
---|---|---|---|---|---|---|---|
a | b | c | d | e | f | g | h |
-8 | -7 | -6 | -5 | -4 | -3 | -2 | -1 |
索引:在[]中给出序号
切片:在[]中给出序号范围
布尔值
布尔值:True、False
逻辑运算和关系运算的结果是布尔值
关系运算符
运算符 | 表达式 | 含义 | 实例 | 结果 |
---|---|---|---|---|
== | x==y | x等于y | ‘ABCD’=='ABCDEF' | False |
!= | x!=y | x不等于y | 'ABCD'!='abcd' | True |
> | x>y | x大于y | 'ABC'>"ABD" | False |
>= | x>=y | x大于等于y | 123>=23 | True |
< | x<y | x小于y | 'ABC'<'DEF' | True |
<= | x<=y | x小于等于y | '123'<='23' | True |
注意:字符串和数字不能进行比较
关系运算符实例
1<3>5 等价于 1<3 and 3<5
逻辑运算符
and运算
逻辑量1 | 逻辑量2 | 结果 |
---|---|---|
False | False | False |
False | True | False |
True | False | False |
True0 | True | True |
只要逻辑量中有一个是False,则结果也为False
or运算符
逻辑量1 | 逻辑量2 | 结果 |
---|---|---|
False | False | False |
False | True | True |
True | False | True |
True0 | True | True |
not运算
逻辑量 | 结果 |
---|---|
False | True |
True | False |
示例
优先级和结和性实例
2.3内置转换函数
函数名 | 含义 |
---|---|
bool() | 根据传入的参数的逻辑值创建一个新的布尔值 |
int() | 根据传入的参数创建一个新的整数 |
float() | 根据传入的参数创建一个新的浮点数 |
complex() | 根据传入的参数创建一个新的复数 |
str() | 创建一个字符串 |
ord() | 返回Unicode字符对应的整数 |
chr() | 返回帧数所对应的Unicode字符 |
bin() | 将整数转换成2进制字符串 |
oct() | 将整数转换成8进制字符串 |
hex() | 将整数转换成16进制字符串 |
list() | 根据传入的参数创建一个新的列表 |
类型转换函数实例
基本格式:int(x[,base=10])
ord函数和chr函数
bin函数,oct函数,hex函数
2.4语句
2.4.1赋值语句
基本形式是“变量=值”的形式
例:基本赋值语句
2.4.2 if语句
分支语句:if语句
if 逻辑表达式: 语句块1 else: 语句块2
例:判断奇偶数
x=int(input()) if x%2==0: print("偶数") else: print("奇数")
为鼓励居民节约用水,自来水公司采取按用水阶梯式计价的办法,居民应交水费y(元)与月用水量x(吨)相关:
当x不超过15吨时,y=4x/3;超过后,y=2.5x-17.5,小数部分保留2位。请编写程序实现水费的计算。
x=float(input()) if x<=15: y=4*x/3 else: y=2.5*x-17.5 print("{:.2f}".format(y))
2.4.3 for语句
循环语句:for语句
for variable in 列表: 语句块
例:遍历列表
for i in [1,2,3,4]: print(i,end=" ")for i in [1,2,3,4]: print(i) i=i+2 print("i+2之后的值") print(i)
结果展示
range函数
range(start,stop,step).
start:计数从start开始。默认是从0开始
例如 range(5)等价于range(0,5)
stop:计数到stop结束,但不包括stop。
例如:list(range(0,5))是[0,1,2,3,4]没有5
step:步长,默认为1.
例如:range(0,5)等价于range(0,5,1)
例:
输入n(n>=10),求1+2+3+...+n之和
n=int(input()) s=sum(list(range(n+1))) print(s)
例:输入n(n>=5)求n!
n=int(input()) factor=list(range(1,n+1)) f=1 for i in factor: f=f*i print(f)
2.4.4 列表推导式
列表是Python最常用数据类型之一:
由零个或多个元素组成,元素之间用逗号分开,整个列表被方括号所包裹
元素类型可以相同也可以不同
通过序号可以引用列表中的元素
支持加法、乘法、比较、索引、切片操作等等
列表推导式(又称列表解析式)提供一种简明扼要的方法创建列表
它可以将循环和条件判断结合,从而避免语法冗长的代码,同时提高程序性能
基本格式:
[expression for item iterable]
带条件的列表解析
列表推导式应用
求1+1/2+...+1/20之和
a=sum([1/i for i in range(1,21)]) print(a)
求1-1/2+1/3-1/4+...之前n项和(n>=10)
n=int(input()) a=sum([1/i if i%2==1 else -1/i for i in range(1,n+1)]) print(a)
求6+66+666+...+66666....6666
n=int(input()) print(sum([int('6'*i) for i in range(1,n+1)]))
2.5 格式化输出
例 华氏-摄氏温度转换表
输入2个正整数lower和upper(lower<upper<100),输出一张取值范围为[lower,upper]、且每次增加2华氏度的华氏-摄氏温度转换表,结果小数部分保留一位。温度转换的计算公式:C=5*(F-32)/9 其中:C表示摄氏温度,F表示华氏温度
lower,upper =input().split() lower,upper=int(lower),int(upper) for i in range(lower,upper+1,2): print(i,"{:.1f}".format(5*(i-32)/9))
format()函数
基本格式:str.format()
0和1表示format函数中的第一和第二个参数
.2f表示小数部分保留两位,四舍五入
课后题:求交错序列的前N项和
输入正整数N,输出序列和,结果保留三位小数
1-2/3+3/5-4/7+5/9-6/11+...+前N项
解法一
n=int(input()) result=0 for i in range(1,n+1): if i%2==1: result=result+i/(2*i-1) else: result=result-i/(2*i-1) print("{:.3f}".format(result))
解法二
n=int(input()) alist=[i/(2*i-1) if i%2==1 else -i/(2*i-1) for i in range(1,n+1)] result=sum(alist) print("{:.3f}".format(result))
三.使用字符串、列表、元组
3.1序列的访问及运算符
3.1.1序列类型容器
示例:
3.1.2取单个元素
注意:字符串根据下标值不能随便修改
3.1.3 字符串和列表切片
示例:取出身份证号中的出生日期
sfh =input() sr=sfh[6:14] print(sr)
示例:取出某一季度的月份
month=['一',‘二’,"三","四","五","六","七","八","九","十","十一","十二"]
示例:取出温度的数值
示例:取后面的字符
3.1.4序列的函数
len()函数:表示有多少个个数
min取最小值 max取最大值
3.2使用字符串
3.2.1 字符串再认识
当字符串中包含单引号时,可将外部的单引号换成双引号。需要使用双引号就在外面使用三引号或者使用单引号,用三引号表示多行元素 r表示保留之前的形式
3.2.2字符串函数
点函数
lower():将字符串中的大写字母全部变为小写
find():找到子字符所在的位置
count():统计某一字符的次数
strip():将两边的空格去掉
rstrip():将右边的空格去掉
lstrip():将左边的空格去掉
replace():替换一串字符串为其它内容
3.2.3字符串和数字之间的转换
3.3.1基本的列表操作
列表中的元素可以是不同的类型
列表是序列类型,之前的所有序列操作对于列表来说都是成立的。
list()函数可以将字符串转换成列表
列表的元素也可以是列表,就称这样的表为广义表
如果将两个列表赋值,改变其中的一个元素,另一个列表中元素也会改变
列表变量赋值之后指向的是同一个地址
列表只是管理者并不是拥有者
如果想另外设置一个不同地址的列表,就需要将列表做切片,比如a1=a2[:]
切片的列表内容个数也可以不相同
del 可以删除列表的某一个元素 del 元素变量
3.3.2 列表的函数
列表.append()往一个列表增加一个元素
列表.extend([7,8,9])列表拼接列表
列表.insert("位置",“元素”)
列表.remove(元素) 只删除第一个元素
列表.pop() 最后一个元素
列表.pop(位置) 删除第几个位置的元素
列表.reverse() 颠倒列表中元素的顺序
列表.index("元素") 查找某个元素所在的位置
3.3.3 列表和字符串之间的操作
split()函数 :以空格作为分隔,当然也可以自带参数
join将列表连接成字符串
3.4 元组的使用
元组和列表几乎没有区别,唯一的区别是元组是由小括号组成,元组是一种不可修改的数据,无法进行元素的赋值,一般的内置函数列表与元组相同唯一不同的是,不能使用能改变元素的函数。
为什么要使用元组,是想让给出的数据不能够被改变
使用tuple函数,用逗号隔开的都是元组
3.5 Python随机模块(随机函数库)
将列表从小到大排序 :sort函数
将列表顺序打乱 导入random库
random.shuffle 将列表顺序打乱
random.choice 随机选择一个元素
随机数是平均分布
random.seed(x) 根据x的值返回确定的数
四.条件循环和其它语句
4.1 条件语句
x=int(input()) if x>0: print("POS") else: print("NEG")
嵌套的if语句
x,y=map(int,input().split())#嵌套的if语句 if x>y: if x>0: print(x) else: print(-x) else: print(y)
if表示数学的分段函数
x=int(input()) y=0 if x>0: y=1 else : if x==0: y=0 else: y=2*x+100 print(y)
x=int(input()) y=0 if x>0: y=1 elif x==0: y=0 else: y=2*x+100 print(y)
4.2 while 循环
s=0 cnt=0 while True: x=int(input()) if x!=-1: s+=x cnt+=1 else: print("结束") break if cnt>0: print(s/cnt) else: print(0)
4.3 for循环
for
else
表示如果for正常执行结束,会再执行else否则就不执行else
示例:判断素数
x=int(input()) isprime=True for k in range(2,x): if x%k==0: isprime=False print("is not prime") break else: print("is prime")
求两个数之间的素数的和和素数的个数
m,n=map(int,input().split()) s=0 cnt=0 for x in range(m,n+1): for k in range(2,x): if x % k ==0: break else: cnt+=1 s+=x print(cnt,s)
4.4 range函数
产生的是列表数列
有两个参数的话表示的是从哪里开始到哪里结束
range的第三个参数表示的是步长
第三个参数要是负数,则可以从大到小排列
4.5异常
4.5.1 异常处理
异常保护机制
语法
try:
执行某语句
except:
发生错误时执行此语句
else执行是try中没有异常就执行else
finally是无论是否有异常都会执行
示例
x=int(input()) t=[1,2,3,4,5] try: print(t[x]) print("hello") except: print("x is not a valid index") else: print("nothing") finally: print("anyway")
输入2时结果
输入5时
x=int(input()) y=int(input()) try: result=x/y except ZeroDivisionError: print("division by zero!") else: print("result is",result) finally: print("executing finally clause")
python常见的标准异常
AssertionError 断言语句(assert)失败 AttributeError 尝试访问未知的对象属性 EOFError 用户输入文件末尾标志EOF(Ctrl+d) FloatingPointError 浮点计算错误 GeneratorExit generator.close()方法被调用的时候 ImportError 导入模块失败的时候 IndexError 索引超出序列的范围 KeyError 字典中查找一个不存在的关键字 KeyboardInterrupt 用户输入中断键(Ctrl+c) MemoryError 内存溢出(可通过删除对象释放内存) NameError 尝试访问一个不存在的变量 NotImplementedError 尚未实现的方法 OSError 操作系统产生的异常(例如打开一个不存在的文件) OverflowError 数值运算超出最大限制 ReferenceError 弱引用(weak reference)试图访问一个已经被垃圾回收机制回收了的对象 RuntimeError 一般的运行时错误 StopIteration 迭代器没有更多的值 SyntaxError Python的语法错误 IndentationError 缩进错误 TabError Tab和空格混合使用 SystemError Python编译器系统错误 SystemExit Python编译器进程被关闭 TypeError 不同类型间的无效操作 UnboundLocalError 访问一个未初始化的本地变量(NameError的子类) UnicodeError Unicode相关的错误(ValueError的子类) UnicodeEncodeError Unicode编码时的错误(UnicodeError的子类) UnicodeDecodeError Unicode解码时的错误(UnicodeError的子类) UnicodeTranslateError Unicode转换时的错误(UnicodeError的子类) ValueError 传入无效的参数 ZeroDivisionError 除数为零
五.集合与字典
5.1集合
特点:元素无序(是指无法指定元素在集合中的位置)、无重复元素
集合的自变量表示是大括号
往集合里加数 用add函数
可以将一个列表通过set函数转换成集合
空的{}表示的是字典
而要表示空集合要用set()
A集合小于B集合,表示A集合是B集合的真子集
A集合小于等于B集合,表示A集合是B的子集
A|B:取并集
A&B :A与B取交集
A^B:对称差运算
A-B: 差值运算
5.2字典
{'key':value}键值对
想要添加元素,直接赋值
5.2.1删除条目
用del语句,删除指定键的字典条目。
del score['张三']
注:如果指定键不存在,则会抛出KeyError异常
min,max分别获得最大最小的key
d.get()也可以获取某一具体的值
示例:统计输入的数字的个数
d={} while True: x=int(input()) if x!=-1: d[x]=d.get(x,0)+1#如果存在就+1 # if x in d: # d[x]+=1 # else: # d[x]=1 else: break print(d)
5.3集合与字典的应用
示例 :处理学生成绩
输入:(以END结束)
学生的学号,姓名
学生的学号,课程,成绩
输出:
表头 学号 姓名 课程1 课程2... 平均分
内容 <学号><姓名>< 成绩1><成绩2><平均分>
数据结构
字典 stuid,键是学号,值是姓名
score,键是课程,值是成绩
stuscore,键是学号,值是字典score
集合course,课程
stuid={} stuscore={} score={} course=set() while True: line=input() if line=='END': break else: s=line.split(',') if len(s)==2: stuid[s[0]]=s[1] elif len(s)==3: score=stuscore.get(s[0],{}) score[s[1]]=int(s[2]) stuscore[s[0]]=score course.add(s[1]) courename=list(course) print('学号'+','+'姓名',end='') for name in courename: print(','+name,end='') print(','+'平均分',end='') print() for id in stuid.keys(): print(id+','+stuid[id],end='') score=stuscore[id] sum=0 cnt=0 for name in courename: print(',',end='') if name in score: print(score[name],end="") sum+=int(score[name]) cnt+=1 print(","+str(int(sum/cnt)))
验证
六.函数
6.1函数定义与调用过程
函数是重用的程序段。它们允许你给一段语句命名一个名字,这是函数定义。
你可以在你的程序的任何地方使用这个名称运行这个语句块,这是函数调用
内置函数不用定义,直接调用。
len("hello")
5
自定义函数语法格式:
def 函数名(参数表):
函数体
如要定义函数: y=x^2+1
def f(x):
value=x**2+1
return value
n=int(input())
y=f(n)
print(y)
求斐波那契数列的前n项
def fibs(n): result=[1,1] for i in range(n-2): result.append(result[-2]+result[-1]) return result print(fibs(5))
注意:函数要先定义再使用
匿名函数--lambda表达式
函数定义的另一种方法是用lambda表达式,它定义了一个匿名函数。lambda的一般形式是关键字lambda后面跟一个或多个参数,紧跟一个冒号,后面是一个表达式。作为表达式,lambda返回一个值。lambda用来编写简单的函数,而def用来处理更强大任务的函数。
g=lambda x,y,z:x+y+z
#把lambda定义的匿名函数赋给函数g
print(g(1,4,5))
练习:定义函数y=sin(x)+1
import math def f(x): y=math.sin(x)+1 return y y=f(3.5) print(y)
6.2函数参数
函数定义时的参数称为形参,这些参数就像变量一样
参数在函数定义的圆括号内指定,用逗号分割。
当我们调用函数的时候,函数中的参数值称为实参
函数形参取得的值是你调用函数时提供的实参。
6.2.1位置参数(按照先后顺序赋值)
Python处理参数的方式要比其他语言更加灵活。其中,最熟悉的参数类型是位置参数,传入参数的值是按照顺序依次赋值给形参,
from math import sqrt def dis(x1,y1,x2,y2):#求平面上两点距离 print("x1={},y1={},x2={},y2={}".format(x1,y1,x2,y2)) return sqrt((x1-x2)**2+(y1-y2)**2) print(dis(1,3,4,5))
6.2.2关键字参数
为了避免位置参数严格的位置要求,调用参数时可以指定对应形式参数的名字,这是关键字参数,它甚至可以采用与函数定义时不同的顺序。
from math import sqrt def dis(x1,y1,x2,y2):#求平面上两点距离 print("x1={},y1={},x2={},y2={}".format(x1,y1,x2,y2)) return sqrt((x1-x2)**2+(y1-y2)**2) print(dis(x1=1,y2=3,y1=4,x2=5))
6.2.3 位置参数和关键字参数混合
如果同时出现两种参数形式,首先应该写的是位置参数,然后是关键字参数。
from math import sqrt def dis(x1,y1,x2,y2):#求平面上两点距离 print("x1={},y1={},x2={},y2={}".format(x1,y1,x2,y2)) return sqrt((x1-x2)**2+(y1-y2)**2) print(dis(1,3,y2=5,x2=4))
6.2.4 默认值参数
当调用方没有提供对应形式参数的值时,你可以指定默认形式参数值。如果你提供实参,在调用时会代替默认值
from math import sqrt def dis(x1,y1,x2,y2=5):#求平面上两点距离 print("x1={},y1={},x2={},y2={}".format(x1,y1,x2,y2)) return sqrt((x1-x2)**2+(y1-y2)**2) print(dis(1,3,4))
默认参数值在函数对象被创建时计算
def init(arg,result=[]): result.append(arg) print(result) init('a') init('b') init(1,[1])
6.2.5数量可变参数
当函数参数数目不确定时,星号将一组可变数量的位置参数集合成参数值的元组
def countnum(a,*b):#计算参数个数 print(b) print(len(b)+1) countnum(3,7,9) countnum(5,8,1,6,89)
收集参数到字典中--**
def countnum(a,**d):#计算参数个数 print(d) print(len(d)+1) countnum(3,x1=9,x2=1,x3=6,x4=89)
print函数的完整表示
print(*obkect,sep=" ",end="\n",file=sys.stdout) object:输出参数,可变数量 缺省值参数 sep="":输出分割符 end="\n":输出函数结束换行 file=sys.stdout:输出到屏幕缺省
实参拆包
*或**都是加在形参的前面,表示不定长参数,分别用来接收不带变量名的多余参数和带有变量名的多余参数,分别将它们以元组和字典的形式接收进函数
当在实参的前面加上星号,就意味着拆包。*表示将序列拆成一个个单独的实参。
可变对象和不可变对象当参数
可变对象和不可变对象当参数,效果可能是不同的
当实参是不可变对象时,形参值改变不会影响实参!
当实参时可变对象时,形参值改变可能会影响实参!
例子1
def change(a,b): a=3 b=b+a x,y=7,9 change(x,y) print(x,y)
def change1(a): a[0]=3 a[1]=11+a[0] l=[7,9] change1(l) print(l)
6.3函数返回值
函数用return语句返回值。
return后面的表达式的值就成为这次函数调用的返回值。
如函数没有用return语句返回,这时函数返回的值为None;如果return后面没有表达式,调用的返回值也为None。
None是Python中一个特殊的值,虽然它不表示任何数据,但仍然具有重要的作用。
示例:求整数M和N区间内素数的个数并对它们求和(2<=M<N)
def isprime(i): for k in range(2,i): if i%k==0: return False return True m,n=input().split() m,n=int(m),int(n) p=[i for i in range(m,n+1) if isprime(i)] print(len(p),sum(p))
返回值是函数
def test(par): return par def test1(): return 1000 def test2(par): return 2000 def f(x): return { 'a':test, 'b':test1, }.get(x,test2) print(f('a')(100)) print(f(4)(100))
集合add函数返回值是None
按列表原来的次序输出非重复元素
l=[2,3,5,8,3,6,8,6,5] seen=set() #集合存放已在列表中的元素 l1=[i for i in l if i not in seen and not seen.add(i)] print(l1)
如果将程序换位
l=[2,3,5,8,3,6,8,6,5] seen=set() #集合存放已在列表中的元素 l1=[i for i in l if not seen.add(i) and i not in seen] print(l1)
l1=[i for i in l if not seen.add(i) and i not in seen]中先执行 add 将没有的函数添加到集合中并且 为True 但是 此时后面的判断条件就为False了
6.4命名空间和作用域
1.变量可被访问范围称为变量的作用域,也称为变量命名空间或变量名字空间。Python程序用命名空间区分不同空间的相同名字。
2.Python解释器启动时建立一个全局命名空间,全局变量就放在这个空间,还建立内置命名空间(built-in namespace).记录所有标准常量名、标准函数名等。在全局命名空间中定义的变量是全局变量。
3.每一个函数定义自己的命名空间,函数内部定义的变量是局部变量。如果在一个函数中定义一个变量x,在另外一个函数中也定义x变量,因为是在不同的命名空间,所以两者指代的是不同的变量。可以通过多种方式获取其他命名空间的变量。
6.4.1全局命名空间
6.4.2局部变量与全局变量
Python语言规定赋值即定义。“var=1”赋值语句定义了变量“var”并赋值为1
全局变量:定义在函数外,作用域是整个程序。
局部变量:定义在函数内,作用域是函数内部。形参也是局部变量
6.4.3局部变量和全局变量同名
def scope(): var1=1 print("函数内部打印结果") print(var1,var2) var1=10 var2=20 scope() print("函数外部打印结果") print(var1,var2)
6.4.4global关键字
如希望在函数中使用全局变量,而不是创建局部变量,需要用global关键字声明
def scope(): global var1 var1=1 print("函数内部打印结果") print(var1,var2) var1=10 var2=20 scope() print("函数外部打印结果") print(var1,var2)
练习
x=100 def f(): y=x #x未定义出错 x=0 print(x,y) f()
纠正
x=100 def f(): x=0 y = x print(x,y) f()
6.5递归
函数调用自身的编程技巧称为递归
递归做为一种算法在程序设计中广泛应用。它通常把一个大型复杂的问题层层转化为一个与原问题相似的规模较小的问题来求解,大大减少了程序的代码量。
递归的能力在于用有限的语句来定义对象的无限集合。一般来说,递归需要终止条件和递归条件。当终止条件不满足时,递归前进;当终止条件满足时,递归返回。编写递归函数时,必须告诉它何时停止递归,从而避免形成无限循环。
斐波那契数列递归定义
斐波那契数列是一个经常使用递归方式定义的序列
fib(0)=1 n=0 (1)
fib(1)=1 n=1 (2)
fib(n)=fib(n-1)+fib(n-2) n>=2 (3)
公式(1)和公式(2)是递归终止条件,公式(3)是递归式
斐波那契数列递归程序
def fib(n):#假定n是正整数,返回第n+1个斐波那契数 if n==0 or n==1: return 1 else: return fib(n-1)+fib(n-2) print(fib(4))
改进斐波那契数列递归程序
pre={0:1,1:1} def fib(n): if n in pre:#可以用in检查字典中是否有n这个关键字 return pre[n] else: newvalue=fib(n-1)+fib(n-2) pre[n]=newvalue#增加字典的条目 return newvalue print(fib(100))
求嵌套列表中数字元素和(返回多个值)
def flatten(items): lst=[] for x in items: if isinstance(x,(list,tuple)) and not isinstance(x,str): for element in flatten(x): lst.append(element) else: if type(x)!=str: lst.append(x) return lst items=[11,2,[3,7],(68,-1),"123",9] l=[i for i in flatten(items)] print(l) print(sum(l))
6.6内置函数
6.6.1 sorted函数
sorted函数对字符串,列表,元组,字典对象进行排序操作。
sort是应用在list上的方法,sorted可以对更多的数据类型进行操作。
即便都是对列表操作,list的sort方法返回的是对已经存在的列表进行操作,而内建函数sorted返回的是一个新的list,而不是在原来的基础上进行的操作。
sorted函数语法
stored(iterable[,key[,reverse]])
iterable --序列,如字符串,列表,元组等。
key -函数,缺省为空
reverse --排序规则
reverse = True 降序,reverse = False 升序(默认)
示例:
students=[('张三',89,15),("李四",80,16),("王五",85,17)]#第二个分量是成绩,第三个分量是年龄 print("按年龄从小到大排序") print(sorted(students,key=lambda s:s[2])) #按年龄从小到大排序 print("按成绩从大到小排序") print(sorted(students,key=lambda s:s[1],reverse=True))#按成绩从大到小降序
6.6.2 map函数
map会根据提供的函数对指定序列做映射。
map函数语法:map(function,iterable,...)
第一个参数function是对参数序列中的每一个元素调用function函数,iterable是序列
返回值的新列表或迭代器,每个元素是调用
function函数的返回值
示例:
print(list(map(lambda x:x**2,[1,2,3,4,5])))#使用lambda匿名函数 print(list(map(lambda x,y:x+y,[1,3,5,7,9],[2,4,6,8,10])))#提供了两个列表,对相同位置的列表数据进行相加
6.6.3 zip函数
zip()函数用于将可迭代的对象作为参数,将对象中对应的元素打包成一个个元组,然后返回由这些元组组成的列表或迭代器。
如果各个迭代器的元素个数不一致,则返回列表长度与最短的对象相同。
zip语法:zip([iterable,...])
参数说明:iterable,... --两个或多个序列
返回值:返回元组列表
a=[1,2,3] b=[4,5,6] c=[4,5,6,7,8] print(list(zip(a,b))) print(list(zip(a,c)))#元素个数与最短的列表一致
示例:字典键值互换
d={'blue':500,'red':100,'while':300}#值不相同 d1=dict(zip(d.values(),d.keys())) print(d1)
6.6.4 eval和exec函数
Python是一种动态语言,它包含很多含义。Python变量类型,操作的合法性检查都在动态运行中检查;运算的代码需要到运行时才能动态确定;程序结构也可以动态变化,容许动态加载新模块等。这两个函数就体现了这个特点。
eval是计算表达式,返回表达式的值。
exec可运行Python的程序,返回程序运行结果。
x,y=3,7 print(eval('x+3*y-4')) exec('print("hello world")')
6.6.5 all和any函数
all()和any()函数将可迭代的对象作为参数。
all函数参数都是True时,才返回True,否则返回False
any函数参数只要有一个为True,就返回True,参数全部时False,返回iFalse
n=47 print(all([1 if n%k!=0 else 0 for k in range(2,n)])) m=15 print(all([1 if n%k!=0 else 0 for k in range(2,n)])) print(any([[],False,0]))#空列表和0都表示False
6.7 程序结构
书的内容按照这样的层次组织:单词、句子、段落以及章。
代码也有类似的自底向上的组织层次:数据类型类似于单词,语句类似于句子,函数类似于段落,模块类似于章。
一个Python程序可以在不同的文件中,这些文件是一个个模块。用import语句引入
import 模块名
模块名是另外一个Python文件的文件名,不包含扩展名,模块是可以运行的程序,
“import 模块名”就是执行文件名为模块名的程序
6.7.1 引入模块中函数的另一种方法
from 模块名 import *
这种方法引入模块中的所有函数,调用的时候不需要再加模块名
from 模块名 import 函数名
这种方法引入模块中的单个函数,调用的时候也不需要再加模块名
6.7.2 创建模块(两文件同一目录)
下面是triangle模块(文件名为triangle.py)
import math def area(a,b,c): s=(a+b+c)/2 return (math.sqrt(s*(s-a)*(s-b)*(s-c)))
主程序是另一个文件(area.py)
import triangle a=12 b=34 c=26 print(triangle.area(a,b,c))
6.7.3 模块名字空间
1.“主程序”指启动一个程序的代码。包含“主程序”的模块,它的模块空间就是全局名字空间
2.模块空间中有:
模块名,它是模块的文件名,但包含“主程序”的模块名,是“ __ main__"
全局变量
函数名
3.dir(模块名 ):显示模块内容
6.7.4 包
我们已使用过单行代码、多行函数、独立程序以及同一目录下的多个模块。为了使Python应用更具可扩展性,你可以把多个模块文件组织成目录,称之为包。包是一个目录,其中包含一组模块文件和一个init.py文件。如果模块存在于包中,使用“import 包名.模块名”形式导入包中模块,用以下形式调用模块,用以下形式调用函数:“包名.模块名.函数”
6.7.5 sys模块
上面的area.py和triangle.py两个文件在同一目录下,通过Python运行主程序area.py,会引用triangle模块,执行函数area。
模块的查找路径:sys.path
如不在同一目录,可用sys模块加入搜索路径后调用
sys模块中的常用量
sys.argv | 从程序外部向程序传递参数 |
---|---|
sys.path | 模块搜索路径的字符串列表 |
sys.stdin | 标准输入 |
sys.stdout | 标准输出 |
sys.stderr | 标准错误输出 |
sys.getdefaultencoding() | 获取系统当前编码 |
6.8习题选讲
输入整数n(3<=n<=7),编写程序输出1,2,...,你、
整数的全排列,按字典序输出。
输入样例:
输入 3
输出:123 132 213 231 312 321
def perm(word): #满足输入要求的n个整数组成的字符串,如“123” result=[] if len(word)==1: #递归结束 result.append(word) return result else: #递归过程 for i in range(len(word)): newword=word[:i]+word[i+1:] #生成去掉一个后的字符串 newresult=perm(newword) #递归调用 for s in newresult: result.append(word[i]+s) return result n=int(input()) s="".join([str(i) for i in range(1,n+1)]) for s1 in perm(s): print(s1,end=" ")
一元多项式相加
用字典表示多项式,键表示指数,值表示系数
a={12:9,8:15,2:3} b={19:26,8:-1,6:-13,2:-3,0:82} def polyadd(a,b): newpoly={} deg=set(a)|set(b) for d in deg: coe=a.get(d,0)+b.get(d,0) if coe!=0: newpoly[d]=coe return newpoly lst=list(polyadd(a,b).items()) print(sorted(lst,key=lambda x:x[0],reverse=True))
七.文件
7.1 文件读写操作
计算机文件,是存储在某种长期存储设备上的一段数据流。所谓“长期存储设备”一般指磁盘、光盘、U盘等。其特点是所存信息可以长期、多次使用,不会因为断电而消失。
计算机文件可分为二种:二进制文件和文本文件
图形文件及文字处理程序等计算机程序都属于二进制文件。这些文件含有特殊的格式以及计算机代码。
文本文件则是可以用文字处理程序阅读的简单文本文件
7.1.1 文件读写操作
7.1.1.1文件读写步骤
1.打开文件
2.处理数据
3.关闭文件
7.1.1.2显示文件内容
textFile=open("7-1.txt","rt",encoding='utf-8') #以文本方式打开 t=textFile.readline() print(t) textFile.close() binFile=open("7-1.txt","rb")# 以二进制方式打开 b=binFile.readline() print(b) binFile.close()
open函数
fileobj=open(filename,mode)
fileobj是open()返回的文件对象
filename是文件的文件名
mode是指明文件类型和操作的字符串
mode的第一个字母表明对其的操作。mode的第二个字母是文件类型:t(可省略)代表文本类型文件;b代表二进制类型文件。
7.1.1.3文件打开模式
文件打卡模式 | 含义 |
---|---|
"r" | 只读模式(默认) |
"w" | 覆盖写模式(不存在则新创建;存在则重写新内容) |
"a" | 追加模式(不存在则新创建;存在则只追加内容) |
"x" | 创建写模式(不存在则新创建;存在则出错) |
"+" | 与r/w/a/x一起使用,增加读写功能 |
"t" | 文本类型 |
"b" | 二进制类型 |
7.1.1.4 文件读写函数
名称 | 含义 |
---|---|
open() | 打开文件 |
read(size) | 从文件读取长度为size的字符串,如果未给定或为负则读取所有内容 |
readline() | 读取整行,返回字符串 |
readlines() | 读写所有行并返回列表 |
write(s) | 把字符串s的内容写入文件 |
writelines(s) | 向文件写入一个元素为字符串的列表,如果需要换行则要自己加入每行的换行符。 |
seek(off,whence=0) | 设置文件当前位置 |
tell() | 返回文件读写的当前位置 |
close() | 关闭文件。关闭后文件不能再进行读写操作。 |
7.1.1.5文件复制
source=open("cj.txt","r") back=open("cjback.txt","w") s=source.read() back.write(s) source.close() back.close()
7.1.2 多行文件读写
用readlines()读写多行文件
f=open("score.txt","r") for line in f.readlines(): print(line) #处理行 f.close()
可用嵌套列表存放多行内容
示例:
学号 姓名 专业 笔试 平时 实验 20101 张三 计算机 65 85 76 20102 李四 金融 86 95 85 20103 王五 经济 86 95 65 20104 丁六 化学 62 75 92
总评=笔试 * 50%+平时 * 25%+ 实验 * 25%
f=open("score.txt","r",encoding="utf-8") # s=f.readlines() # print(s) head=f.readline() newhead=head[:6]+head[6:17]+head[17:-1]+" 总评成绩" print(newhead) for line in f.readlines(): l=line.split() s=round(int(l[3])*0.5+int(l[4])*0.25+int(l[5])*0.25,2) l[4]=" "+l[4] l[5]=" "+l[5]+" " print(" ".join(l)+str(s)) f.close()
7.1.3 输入输出重定向
sys.stdin 标准输入
sys.stdout 标准输出
sys.stderr 标准错误输出
import sys #c从文件读入变为从键盘输入,改变输入源 s=sys.stdin.readlines() print(s)
import sys s=sys.stdin.read();strs=s[:s.finf('#')] for k in set([i for i in strs if i.isalnum()==False and i!="_"]): strs=strs.replace(k," ") strs=strs.rstrip(" ").lower().split() counts=dict() for i in strs: k=i[:15] if k not in counts: counts[k]=1 else: counts[k]+=1 ans=sorted(counts.items(),key=lambda x:(-x[1],x[0])) print(len(counts)) for i in range(0,int(0.1*len(counts))): print(str(ans[i][1])+":"+ans[i][0])
7.2 用Pandas模块读写常见格式文件
Python的模块函数分三个层次:
一.内置函数
不用import语句引入,它里面的函数可直接调用。
二.标准模块函数
用import语句引入后再调用,但不必安装。如math库
三.第三方模块函数
需要安装,再用import语句引入模块后才能调用里面的函数,如Pandas模块
7.2.1第三方库安装
PyPI · The Python Package Index
pip命令安装
pip install pandas #安装pandas模块
7.2.2 Pandas模块
Pandas是Python的一个数据分析包
Pandas最初被作为金融数据分析工具而开发出来,Pandas为时间序列分析提供了很好的支持。Pandas是基于Numpy的一种工具。
Pandas纳入了大量函数和一些标准的数据模型,提供了高效操作大型数据集所需的工具,提供了大量能使我们快速便捷地处理数据的函数和方法,让Python成为强大而高效的数据分析环境。
7.2.3 Plotly 模块
Plotly是一个基于JavaScript的动态绘图模块。Plotly的绘图效果与我们在网页上看到的动态交互式绘图结果是一样的,其默认的绘图结果是一个HTML网页文件,通过浏览器就可以查看。
Plotly有着强大又丰富的绘图库,支持各种类型的绘图方案。
Plotly是基于JavaScript的绘图库,所以其绘图结果可以与web应用无缝集成。
Plotly最初是一款商业化的绘图软件,由plotly.js开源之后,我们可以使用本地的离线模式进行绘图,不依赖于官方的服务器,使得绘图速度更快,而效果与在线绘图一样。
离线模式: from plotly。offline import plot
7.2.4 DataFrame 数据类型
DataFrame是Pandas库的一种数据类型。DataFrame是一个行和列都具有标签的表格,它与Excel电子表格并无不同。DataFrame使用非常方便,当你处理二维表格数据时,都应该使用它们。DataFrame可由元组、列表、字典或另一个DataFrame构造出来。
7.2.5 由列表产生DataFrame变量data
准备:安装pandas模块和plotly模块
7.2.5.1在PyCharm中安装模块
1.打开file中的Settings
2.配置库查询网址
点击加号
3.点击 Manage Repositories
4.配置网址
Simple Index
PyPI · The Python Package Index
5.搜索模块,点击安装
from plotly.offline import plot from plotly import figure_factory as FF import pandas as pd data=pd.DataFrame([["201101","张三","计算机类",65,85,76],["201102","金融类","李四",75,80,76],["201103","化学类","王五",85,82,74], ["201104","医学类","丁柳",95,85,100],["201105","经济学类","徐兵",65,75,72]],columns=("学号","姓名","专业","笔试","平时","实验")) table =FF.create_table(data) #用plotly产生输出表格 plot(table,show_link=False)
7.2.6 用DataFrame计算总评分
from plotly.offline import plot from plotly import figure_factory as FF import pandas as pd data=pd.DataFrame([["201101","张三","计算机类",65,85,76],["201102","金融类","李四",75,80,76],["201103","化学类","王五",85,82,74], ["201104","医学类","丁柳",95,85,100],["201105","经济学类","徐兵",65,75,72]],columns=("学号","姓名","专业","笔试","平时","实验")) #data变量中增加一列 data["总评成绩"]=data["笔试"]*0.5+data["平时"]*0.25+data["实验"]*0.25 table =FF.create_table(data) #用plotly产生输出表格 plot(table,show_link=False)
7.2.7 用pandas读写各种类型文件
read_csv | to_csv | 读写csv文件 |
---|---|---|
read_excel | to_excel | 读写excel文件 |
read_json | to_json | 读写json文件 |
7.2.8 读取CSV文件
from plotly.offline import plot from plotly import figure_factory as FF import pandas as pd data=pd.read_csv("score.csv",encoding="GBK") table=FF.create_table(data) #产生表格 plot(table,show_link=False)
“GB2312”、"GBK"和“CP936”都是用两个字节表示中文的编码。
“GB2312”是国标码,“GBK”是“GB2312”的扩展,“CP936”是在“GB2312”基础上开发的汉字编码
7.2.9 写网页文件
产生网页文件“score.html”
from plotly.offline import plot from plotly import figure_factory as FF import pandas as pd data=pd.read_csv("score.csv",encoding="GBK") table=FF.create_table(data) plot(table,filename='score.html',show_link=False)
7.2.10 读写Excel文件
首先安装xlrd模块
读score.xlsx文件
写入score.xlsx文件
如果安装第三方模块不成功
使用
pip install 包名 -i Simple Index --trusted-host pypi.douban.com
import pandas as pd data =pd.read_excel("score.xlsx") data["总评"]=data["笔试"]*0.5+data["平时"]*0.25+data["实验"]*0.25 data.to_excel("scoregp.xlsx",index=0)
7.2.11 JSON文件读写
JSON文件主要有两种结构:
“键/值”对的集合:不同的语言中,它被理解为对象,记录,结构,