python入门笔记(掌握一门语言的四分之一)
基础
字符串
import keyword
from operator import indexprint(123) # 输出整型数值
print(12.3) # 输出浮点型数值
print(0x1011) # 输出16进制转化为十进制
print(0b1011) # 输出2进制转化为十进制
print(3 + 4) # 输出含有运算符的十进制
print("string") # 输出字符串
print('helloworld') # 输出字符串
print('hello\rworld(over)')#回车覆盖
print(ord('家')) #返回字符码
字符串的驻留机制
'''字符串为不可变字符序列,不同的字符串存放在字符串的驻留池中相同的字符串只保留一份拷贝,后续创建相同的字符串不会开辟新空间,而是直接引用同一个地址'''
a='python'
b="python"
c='''python'''
print(id(a))
print(id(b))
print(id(c))
'''交互模式下(cmd_python),的驻留情况1、字符串长度为0或12、符合标识符(下划线,字母,数字的组合)的字符串3、只在编译时驻留,而非运行时4、-5到256之间的整数'''
第三种情况:
a='abc'
b='ab'+'c'
c=''.join(['ab','c'])
print(a is b)
print(a is c) #False 因为c的值是在运行时候赋值的,而非编译
a=-6
b=-6
print(a is b) #在交互式环境下显示False
强制指向同一个空间
import sys
a='abc%'
b='abc%'
print(a is b)
字符串的查询操作
a='Hello,Hello'
print(a.index('lo')) #3,第一次出现的位置,不存在抛出ValueError
print(a.find('lo')) #3,第一次出现的位置,不存在返回-1
print(a.rfind('lo')) #9,最后一次出现的位置,不存在返回-1
print(a.rindex('lo')) #9,最后一次出现的位置,不存在抛出ValueError
大小写转换方法
'''s.upper() 所有变大写s.lower() 所有变小写s.swapcase() 大写变小写,小写变大写s.capitalise()首字符字母大写,其他小写s.title() 每个单词第一个字母大写'''
print(a.upper()) #HELLO,HELLO
print(a.lower()) #hello,hello
print(a.swapcase()) #hELLO,hELLO
print(a.capitalize()) #Hello,hello
print(a.title()) #Hello,Hello
字符串内容对齐操作
'''s.center() 居中对齐,参数1:宽度,参数2:填充符(默认空格),设置宽度小于实际宽度,返回原字符串s.ljust() 左对齐,参数1:宽度,参数2:填充符(默认空格),设置宽度小于实际宽度,返回原字符串s.rjust() 右对齐,参数1:宽度,参数2:填充符(默认空格),设置宽度小于实际宽度,返回原字符串s.zfill() 右对齐,左边用0填充,参数:字符串宽度,小于等于字符串宽度,返回字符串本身'''
s='hello*world*python'
print(s.center(20,'*'))
print(s.ljust(20,'*'))
print(s.rjust(20,'*'))
print(s.zfill(20))
print(s.zfill(8))
劈分操作
'''s.split() 从字符串左边开始劈分,默认劈分字符为空格,经过最大次劈分后,剩下的子式单独作为一部分。返回列表,参数:劈分符,最大劈分次数s.rsplit() 从字符串右边开始劈分,默认劈分字符为空格,经过最大次劈分后,剩下的子式单独作为一部分。返回列表,参数:劈分符,最大劈分次数'''
print(s.split('*',1 )) #分割不同的单词
判断字符串操作
'''s.isidentifier() 判断字符串是不是合法标识符s.isspace() 判断字符串是不是全部由空白字符(空格换行水平制表符)组成s.isalpha() 判断字符串是不是全部由字母组成s.isdecimal() 判断字符串是不是全部由十进制数字组成s.isnumeric() 判断字符串是不是全部由数字组成s.isalnum() 判断字符串是不是全部由字母和数字组成'''
print('张三_123'.isidentifier()) #True
print('张三'.isalpha()) #True
'''除了阿拉伯数字以外,其他isdicimal()方法都是Falseisnumeric()方法中,1二Ⅲ④都是数字'''
print('④'.isnumeric())
字符串的替换和合并
'''s.replase() 参数:被替换的子串,替换成的字符,最大替换次数。s.join() 列表或元组的字符串合并成一个字符串'''
s=['hello','python','world']
print('*'.join(s))
print('*'.join('python'))
s='小白兔白又白两只耳朵竖起来'
print('了'.join(s))
字符串的比较
'''运算符:> < >= <= == !=比较规则:先比较第一个字符,如果相等,继续比较。。。比较原理:比较的是字符的原始值,调用内置函数ord()可以得到指定字符的原始值chr()是ord()的互相对应函数,chr()函数可以用原始值得到字符'''
a='apple'
b='app'
print(a > b)
print(ord('a'),chr(ord('l')))
比较:is 和 ==
#==:值相等, is:id相等
字符串的切片操作:将产生新的字符串
print(id(a))
a=a[:2]
print(a,'\t',id(a)) #a重新分配地址
格式化字符串 % 占位符
name='ming'
age=20
print('我叫%s,今年%d岁' % (name,age))
#{}占位符
print('我叫{0},今年{1}岁'.format(name,age))
#f-string
print(f'我叫{name},今年{age}岁')
精度和宽度
'''% num.int f: num表述宽度(宽度不够左边补空格),int表示精度(保留几位小数)'''
print('{0:.3}'.format(3.141592654)) #0表示索引(可省略),3表示保留3位数
print('{0:10.3f}'.format(3.141592654)) #3f表示保留三位小数,10表示宽度
字符串的编码转换
'''编码:将字符串转化成二进制数字'''
a='唧唧复唧唧'
print(a.encode(encoding='GBK')) #GBK:国标扩展,编码格式,一个中文占两个字节
print(a.encode(encoding='UTF-8')) #一个字节占三个字节
byte=a.encode(encoding='GBK')
print(byte.decode(encoding='GBK')) #解码
数据输出到文件中
- 关键字列表
fp=open('D:/text.txt', 'a+') # 函数open(‘路径’,‘打开方式(读写)’)
#print(keyword.kwlist,file=fp) #输出
fp.close()
变量
- 变量不需要定义类型
name='张三' \'李四'
print(name)
print(name[0]) #字符串自动带入为数组
number=0x123 #十进制:291
print(number)#print(number[0]) #报错,因为这里自动定义为int型号
number_string='123'
print(number_string[0],number_string[1])
number='一二三'
print(number) #变量迭代过程:删除原内存,重新分配空间并且重新更改新的数据类型
number=True #布尔类型区分大小True/False
print(number,'\n',type(number))
进制
#二进制:0b, 8进制:0o 十六进制:0x
#浮点数偏差
n1=1.1
n2=2.2
print(n1+n2) #输出结果3.3000000000000003from decimal import Decimal
print(Decimal(n1)+Decimal(n2)) #输出3.300000000000000266453525910
print(Decimal('1.1')+Decimal('2.2')) #输出3.3
利用三引号进行连续输出
print('''小时候总想长大
长大后总想变小
时间赋予我们意义''')
数据类型转换
print(len(number_string))
age=21
# print('我叫'+name+‘今年’+age) 不能同类型输出流
print('我叫',name[0], name[1],'今年',age,'岁') #这样可以
print('我叫' + name[0] +name[1] + '今年' + str(age) + '岁')
'''嘿嘿嘿我是多行注释
嘿嘿嘿'''
#规则:文字类和小数string不能转换为int,文字类不能转换为float
输入函数
dinner = input('晚饭吃了啥?')
print(dinner)
a=input('请输入第一个数')
b=input('请输入第二个数')
print('a+b=' ,a + b) #输出12 13,并没有进行运算
print(type(a),type(b)) #输入类型自动定为string类
'''a=int(a)
b=int(b)'''
#或者在输入行中转换:a=int(input(''))
print('a+b=', a + b)
运算符
- 普通运算符
print(11/2) #直接输出浮点数
print(11//2) #整除运算符
print(11%2) #取余数
print(2**4) #次方运算
- 赋值运算符:从右往左,所有编译器默认
a=b=c=3 #链式赋值
print(id(a),id(b),id(c)) #地址相同,相当于引用同一个参数
'''语言特性:免除参数类型定义的过程,底层将自动为变量取类型'''
a+=20
print(a,type(a))
a-=3
print(a,type(a))
a*=2
print(a,type(a))
a/=3
print(a,type(a))
a//=2
print(a,type(a))
'''以上运算,输出结果为
23 <class 'int'>
20 <class 'int'>
40 <class 'int'>
13.333333333333334 <class 'float'>
6.0 <class 'float'>'''
解包赋值
a,b,c=20,10,50
print(a,b,c) #左右相对应数量
- 利用此语言特性进行数值交换
a,b=b,a
print(a,b)
#对象id对比
print('a 和 b是同一个对象吗',a is b) #False
print(id(a),id(b))
print(a is not b) #True
逻辑运算符
'''与或非分别对应:and or not'''
a=True
print(not a)'''目标是否在某个对象内部:in , not in'''
print('================================')
s='windows'
print('w' in s)
print('s' not in s)
print('============位运算===============')
'''位的与或和位移: &| >>and<<
位移: 左移:高位溢出,低位补零右移,高位补零,低位截至优先级:方,乘除,位移,位逻辑,比较,逻辑(布尔),赋值
python 每一个对象都有一个布尔值
以下对象布尔值为False:
False\数值0\ None\空字符串\空列表\空元组\空字典\空集合 取布尔值函数:bool()'''
#print(bool(False)) #False
print(bool(0),bool(0.0)) #数值0
print(bool(None)) #None
print(bool('')) #空串
print(bool("")) #空串
print(bool([])) #空串
print(bool(list())) #空列表
print(bool(())) #空列表
print(bool(tuple())) #空元组
print((bool({}))) #空元组
print(bool(dict())) #空字典
print(bool(set())) #空集合
静态语言和动态语言多态的区别:
'''继承方法重写父类指向字类对象python是动态语言
'''
分支循环
if else
'''语法结构:if 语句:else:'''
num=int(input('请输入一个整数'))
if num%2==0:print('偶数')
else:print('奇数')
print('========多分支if elif=========')
if num>=90 and num<=100:print('A')
elif num>=80 and num<=90:print('B')
elif num>=70 and num<=80:print(('C'))
else:print('成绩有误')
'''语言特性:连续判断'''
if 90<=num<=100:print('A')
elif 80<=num<=90:print('B')
elif 70<=num<=60:print('C')
elif 60<=num<=50:print('D')
elif num<=60:print('E')
else:print('成绩有误')
'''判断表达语法优化'''
a=int(input('请输入第一个数值'))
b=int(input('请输入第二个数值'))
print( (a,'大于等于',b) if a>=b else (a,'小于等于',b))
range序列
r=range(10) #生成10个元素的序列,起头默认为0,步长默认为1
print(list(r))
r=range(0,10) #range(start,stop)前闭后开区间,步长1
print(list(r))
r=range(0,20,2) #range(start,stop,step):前闭后开
print(list(r))
print(10 in r)print('============循环============')
'''while 条件:循环体'''
a=1
while a<10:print(a)a+=1 #python中没有a++
- python中的求和函数
a=range(0,101,2)
print(sum(a))
print('=========================')
summ=0
a=1
while a<=100: #嵌套分支if not a%2:summ+=aa+=1
print(summ) #输出同样结果
for in 遍历对象
'''for 对象 in 遍历元素'''
for item in "Python": #”“和’‘都代表同一个数据(对象)类型print(item)
print(item) #此处的对象创建为只有一个元素的字符数组
'''
a=0
for item1[a] in 'Python':a+=1
print(a)
'''
#不允许以上运行,在当前库中for in仅允许创建的对象为一个元素
for i in range(11):print(i)
print(i)
- 如循环中,不需要用到自定义变量,可用下划线_代替自定义变量
for _ in range(5): #输出5次helloprint('hello')
break 跳出循环
for _ in range(1): #注意缩进格式psw=input('请输入密码:')if psw=='8888':print('密码正确')breakelse:print('密码不正确')
continue 语句实现循环控制
'''continue和pass区别,
continue:跳过本次循环,不论下面有多少语句
break: 跳出循环
pass: 只起到占位作用,后面的语句回继续执行'''
for _ in range(1):pwd=input('请输入密码:')if pwd!='8888':print('密码不正确')continueelse:print('密码正确')
#循环else语句:循环中没有遇到break语句时候执行else(循环中,没有遇到break认为非正常退出,返回False,触发执行else中语句 for _ in range(2):pwd=input('请输入密码:')if pwd=='8888':print('密码正确')breakelse:print('密码不正确') else:print('输入两次密码错误')
嵌套循环
for i in range(4): #4行for j in range(i+1): #range()中i初始值为0时,直接跳出该循环print('*',end='\t') #为末尾end传递一个空字符串,实现不换行输出
print('')
数据结构
列表
# 可以存储多个元素,相当于数组,但更加具有包容性,不需数组内部元素为同一种类型
a=10 #变量:一个对象的引用
lst=['hello' , 12 , 13.5]
print(type(list[0]) , type(list[1]) , type(list[2]))
'''输出结果:<class 'types.GenericAlias'> <class 'types.GenericAlias'> <class 'types.GenericAlias'>显示数据类型为
‘通用型’
list内部存储的为引用'''
列表创建的两个方法
# 方括号 和 内置函数list()
lst=[1,2,3]
lst2=list([1,2,3])
print(lst , lst2)
#特性:顺序存放,空间连续,索引映射可以为负数,根据需要动态分配内存
print(lst[-1],lst[-3])
获取索引内置函数index
print(lst.index(2)) #排序为0开始 0123456789
lst=['hello','world',56,'hello','12',58,'strike']
print(lst.index('hello',1,4)) #从索引为1到4之间(左闭右开区间)寻找‘hello’,程序报错,找不到
切片操作
print(lst[0:6:2]) #lst[start:stop:step]左闭右开 , 默认start为0,stop为最后一个元素(包括),步长为1#step为负数切片默认第一个元素为最后一个元素,最后一个元素为第一个元素
列表元素的遍历:for in
for item in lst:print(item,end=', ')
print()
print(item)
添加元素
'''append()在末尾添加,extend()在末尾添加至少一个元素,insert()在列表插入一个元素'''
lst.append(100)
print(lst)
lst2=[10, 20 ,30 ,40 ,8.5]
lst.extend(lst2)
print(lst)
lst.insert(2,90) #在索引为2的位置添加一个元素90,原本在2的元素后移
print(lst) #输出['hello', 'world', 90, 56, 'hello', '12', 58, 'strike', 100, 10, 20, 30, 40, 8.5]
剪切操作
lst[1:]=lst2 #将后面的元素替换
print(lst) #输出['hello', 10, 20, 30, 40, 8.5]
lst[1:1]=lst2 #不剪切其他元素
print(lst) #输出['hello', 10, 20, 30, 40, 8.5, 10, 20, 30, 40, 8.5]
lst[-2:-3]=lst2 #在-2到-3之间插入元素,不覆盖,不删除(不论stop在何处,都是一样的结果)
print(lst)
print(id(lst))
lst[-3:]=lst2 #在-3处插入覆盖包括-3
print(lst)
print(id(lst))
删除列表中元素
lst=[10, 20, 30, 40, 50, 60, 99, 'python']
lst.remove('python') #删除一个元素,重复发元素只删除第一个
print(lst)
lst.pop(1) #删除索引为1的元素
lst.pop() #删除最后一个元素
#此时lst为:[10, 30, 40, 50, 60]
切片删除,产生新的列表对象
new_lst=lst[1:4] #左闭右开
print(new_lst)
print(lst)
print(id(lst),id(new_lst)) #原lst被分配到一个新的空间,lst:1763910987712 ,new_lst:1763910987648
切片删除,不产生新列表
lst[1:3]=[]
print(lst,id(lst))
lst.clear() #清楚列表的所有元素
print(lst) #输出空列表,列表所在空间并未删除
del lst #将列表空间清除内存
del lst2
del new_lst
#print(lst) #报错,lst未定义:NameError: name 'lst' is not definedlst=[10, 20, 30, 40, 50, 99]
修改值
lst[5]=60
print(lst)
lst[1:3]=[200, 300, 400, 500] #将索引为1到3的元素(左闭右开)替换
print(lst)
sort()方法
lst=[85,62,43,29,995,35,615,24,32,2]
print('排序前:', lst, id(lst))
lst.sort()
print('排序后列表:', lst, id(lst)) #列表对象没有改变
lst.sort(reverse=True) #降序
print(lst)
内置函数 sorted()
lst=[85,62,43,29,995,35,615,24,32,2]
new_lst=sorted(lst)
print(new_lst, id(new_lst))
new_lst=sorted(lst,reverse=True)
print(new_lst,id(new_lst)) #两个new_lst对象都是新的引用
生成列表方法
lst=[i for i in range(1,10)]
字典
字典创建的两种方式
# 无序序列,双射集合:key->value,可变序列
scr={'ming':100, 'hong':95, 'gang':86}
print(scr)
print(type(scr))
student=dict(name='jac',age=22)
print(student)
- 空字典
scr={}
字典元素的操作
- 字典元素的获取
scr={'ming':100, 'hong':95, 'gang':86}
print(scr['gang'])
print(scr.get('ming')) #字典的get方法,如果元素不存在,程序不会报错,方法返回None
print(scr.get('qiang', 404)) #当元素不存在,返回默认值为404(可以为其他数值)
#字典的判断:in 和 not in
字典的删除
del scr['gang']
print(scr)
scr.clear() #清空字典元素
print(scr)
scr['chen']=100
print(scr)
scr['chen']=96 #修改操作
获取视图
print('===================')
scr={'ming':100, 'hong':95, 'gang':86}
ky=scr.keys()
print(ky, '\t \t', type(ky)) #dict_keys(['ming', 'hong', 'gang']) <class 'dict_keys'>
vilus=scr.values()
print(vilus, '\t \t',type(vilus))
i=scr.items() #取出元组
print(i)
print(list(i)) #转换为元组列表输出
字典元素的遍历
for item in scr:print(item,scr[item],scr.get(item))
print(item) #遍历基于关键字,因此这里for in 是基于关键字的值
字典关键词不允许重复赋值
scr={'name':'gang', 'name':'ming'}
print(scr) #赋值覆盖 {'name': 'ming'}
#字典为无序的,d={lst:100} 报错,lst类型为不可哈希值,不可以哈希存储
#字典浪费大内存空间:空间换时间的数据类型,查找方便
字典生成
# 将两个列表的元素组合成为字典:内置函数zip()
nam =['hong', 'jac', 'lisa', 'peng', 'zhang']
age =[21,22,20,21,28]
student={nam.upper():age for nam, age in zip(nam, age)} #upper()方法为将字母大写
print(student) #如果元素不对称,只遍历最少存在部分
new_student={'HONG':21, 'JAC':22, 'LISA':22, 'ZHANG':19, 'TING':22}
student.update(new_student) #更新操作:有新的变化就改变
print(student)
new_student=student.copy() #浅拷贝
student.pop('PENG') #单个删除
print(student)
num=dict.fromkeys([1,2,3],['one','two','three']) #创建并且返回一个薪字典,前为key,后为value,默认value为None
print(num) #此处不能分别赋值
student.popitem() #删除最后一个键和值
print(student)
print(student.setdefault('ZHANG',23))
'''第一个参数为key,如果key存在,返回该key对应的value,否则将key插入字典并将其value设为函数给定值,默认值为None'''
print(student.setdefault('kiven'))
print(student) #{'HONG': 21, 'JAC': 22, 'LISA': 22, 'ZHANG': 19, 'kiven': None}
print(student.__len__()) #返回字典key数量的多少
元组
'''可变序列: 列表 字典:可以增删改不可变序列: 字符串 元组 改变内容之后地址改变'''
t=('python', 56, 12.8)
print(t, type(t))
t1=tuple(('hello', 'world', 98)) #两个括号
print(t1)
t2='python','hello','world'
print(t2)
t3='hello',
print(t3,type(t3)) #如果元组只含有一个元素,需要用逗号(小括号可以删除)
- 空元组
t4=() print(type(t4))
元组的特性:只可读性,元组存储的对象不可改变
'''如果元组对象本身不可对象(数值,str。。。),则不可以再引用其他对象如果元组中对象是可变对象(dict,list),则可改变对象的引用不许改变(如lst时,不可将元组中的引用地址改变),但数据可以改变(如引用对象为lst,那么可以对这个lst进行增删改)'''
t=(10,[10,20,30],99)
print(t)
#t[0]=1 #报错,元组对象不可修改
t[1].append(40) #可以修改可变对象的数据
print(t)
#元组的for in 遍历
for item in t:
print(item) #可读
集合
集合的创建
# 可变数据类型:没有value(只有键)的字典(哈希取址)
s={2,3,4,5,5,6,7,7,5}
print(s) #不重复性
s2=set(range(6))
print(s2,type(s2))
s3=set([2,1,3,6,6,6,8,7,5,4])
print(s3,type(s3)) #将列表转换成集合
s4=set((1,2,3,56,86,3,2,5,))
print(s4,type(s4)) #元组转换:元组储存无序
s5=set('python')
print(s5) #无序
- 空集合的定义方法
#s6={} 不行,定义类型为空字典
s6=set()
print(type(s6))
- in 和 not in判断集合元素
集合的增加元素操作
s6.add(1)
print(s6)
s6.update({200,'p'}) #需要花括号
print(s6)
s6.update(['y',200,1,3])
print(s6) #重复元素不添加
删除操作
s6.remove(200)
s6.discard('p') #没有该成员忽略,有此成员删除
print(s6)
s6.pop() #任意删除,不能添加参数
print(s6)
s6.clear()
print(s6) #清除
s1={1,2,3,4}
s2={3,2,1,4}
s3={12,3,1,2,4,5,6,7,8,9}
print(s1==s2) #只判断元素
子集判断
print(s3.issubset(s1)) #s3不是s1子集
print(s1.issubset(s3)) #s1是s3子集
超集判断
print(s3.issuperset(s1))
是否有交集判断
print(s3.isdisjoint(s1)) #没有交集是True
集合的数学操作
- 交集
print(s1.intersection(s3))
print(s1 & s3)
- 并集
print(s1.union(s3))
print(s1 | s3)
- 差集
print(s3.difference(s1))
print(s3-s1)
- 对称差
print(s1.symmetric_difference(s3))
print(s1 ^ s3)
集合生成式
s3={ i*i for i in range(10)}
print(s3) #无序
函数
函数的定义
def sum(a=0, b=0, str='function called'):c=a+bprint(str)return c
print(sum(10 ,20))
print(sum())
print(sum(str='hello',b=10,a=6)) #参数的指向赋值
函数调用参数的方式
# 调用引用
def fun(a=0, b=[0,0,0]):print('a=',a,'id of a:',id(a))print('b=',b,'id of b:',id(b))a=100 #此时a的引用对象id改变b.append(10)print('a=',a,'id of a:',id(a))print('b=',b,'id of b:',id(b))b=[1,2,3,4]print(b,id(b)) #b的id也发生了改变,此时b不再是n2的引用,而是新对象:列表[1,2,3,4]的引用
n1=11
n2=[11,22,33,44]
print('id n1:',id(n1))
print('id n2',id(n2))
fun(n1,n2)
print('n1:',n1,id(n1))
print('n2:',n2,id(n2)) #调用对象是一个指针,对指针地址不产生影响,但可以对指针所指的对象进行数据的修改
'''底层:对a进行赋值改变时,a引用的对象的指针将改变,并不影响原来n1的数值,n1一直都是原来数值的引用参数传递过程:将不可变对象传进函数时,形参等于原对象的另一个引用,当函数过程中对形参进行改变时,底层分配一个新的对象给形参,此时形参变成新对象的引用,原参数依然是原对象的引用'''
函数的返回
'''1.没有返回值,可以忽略return,返回None2.返回值只有一个,直接返回类型3.返回值多个,返回元组
'''
def fun1():print('hello')
print(fun1())
函数的参数定义
'''个数可变的位置参数定义函数无法确定传递的实参数量多少使用*定义个数可变的位置形参结果为一个元组个数可变的关键字形参定义函数无法确定传递的关键字实参个数使用**定义个数可变的关键字形参结果为一个字典【注】:以上的两种参数只能是一个
'''
def fun_a(*args):print(args)
fun_a(10,20,30)
def fun_b(**kwargs):print(kwargs)
fun_b(a=10)
fun_b(a=10, b=20, c=30)
def fun_c(*args,**kwargs):pass
'''
def fun_d(**kwargs,*args):pass #报错,在函数定义过程中,既有个数可变的关键字形参,也有个数可变的位置形参要求*args在**kwargs之前
'''
函数的调用
def fun_1(a,b,c): #函数调用时的参数传递,为位置传参print(a,b,c)
lst=[11,22,33]
fun_1(*lst) #将列表中的每个元素转换成位置实参传入,lst中元素不可以大于参数个数
dic={'c':111,'a':222,'b':333}
fun_1(**dic) #将字典的value传入,其中不比较关键字的值,只按照位置传递
print('============')
def fun_2(a,b,*,c,d): #在*后的参数只能采用关键字实参传递print(a)print(b)print(c)print(d)
#fun_2(2,3,4,5) #报错
fun_2(2,3,c=4,d=5)
#以下几种顺序
def fun_3(a,b,*,c,**kwargs):pass
def fun_4(a,b,*args,**kwargs):pass
#def fun_5(a,*,b,c,*args): #报错
# pass
递归函数
def fun_revs(a):if a-1:return a+fun_revs(a-1)else :return a
print(fun_revs(5))
递归的应用:斐波那契数列
def fbnq(a):if a==1:return 1elif a==2:return 1else:return fbnq(a-1)+fbnq(a-2)
print(fbnq(6))
输出数列
for i in range(1,7):
print(fbnq(i),end=' ')
调试
- 被动bug的异常处理
try except 语句
try:a=int(input('请输入第一个数:'))b=int(input('请输入第二个数'))result=a/b
except BaseException as e:print('错误:',e)
else:resultprint('结果:',result)
finally:print('无论是否产生异常,总会执行的语句')print('谢谢你的使用')
print('程序结束')
'''常见异常类型ZeorDivisionError 除0IndexError 序列中没此索引KeyError 映射中没有这个键位NameError 未声明/初始化对象(没有属性)SyntaxError Python语法错误
ValueError 传入无效参数
'''
traceback模块打印异常信息
import traceback
try:raise Exception('i\'m obviously an error') #自行引发异常
except Exception as reason:print('错误类型:',reason)
#raise Exception('i\'m obviously an error') #报错,Exception:i'm obviously an errorprint(dir([])) #dir查看模块列表
print(dir()) #dir()获得当前模块的属性列表
a=10
print(a.__sizeof__()) #对象的sizeof方法下'''
if __name__=='__main__':try:1/0except Exception as e:traceback.print_exc() #得到具体的错误,以及定位到出错的位置
'''
#调试使用Shift+F9
类
类的创建
class Student: #规范:首字母大写location='广东' #共有属性(修改共享化)def __init__(self,name,age): #等于C++中的构造函数self.name=name #私有属性(修改私有化,不共享)self.age=agedef info(self): #实例方法print('我的名字是:',self.name,'年龄:',self.age) #self是自身对象,相当于this指针def eat(self):print(self.name,'是干饭王')@classmethoddef fun1(cls):print('类方法')@staticmethod #使用stativmethoddef fun2():print('静态方法')
print(id(Student))
print(type(Student))
print(Student)
创建对象的方法
n3=Name_class('zhang',10)
print('id of obj:n3 is :{0}'.format(id(n3))) #反映出self就是n3
n4=Name_class.__new__(Name_class,'zgr',56) #和n3=Name_class('zhang',10)相同
stu1=Student('zhang',20) #自动调用构造函数构建
print(id(stu1))
print(type(stu1))
Student.eat(stu1)
stu1.eat()
类的属性、方法
'''类属性:除方法之外的变量,被所有类共享实例方法:被实例对象调用类方法:使用类名直接访问的方法静态方法:使用类名直接访问类中定义了同名的方法时,调用方法会执行最后定义的方法静态方法和类方法的区别1、类方法:用修饰器@classmethod来标识其为类方法,类方法第一个参数必须是类对象,一般以cls作为第一个参数2、静态方法:需要通过装饰器@staticmethod来进行修饰静态方法既不需要传递类对象也不需要传递实例对象(形参没有self/cls,参数没有要求)。静态方法也能够通过实例对象和类对象去访问。无视self,而将这个方法当成一个普通的函数使用。使用场景:当方法中 既不需要使用实例对象(如实例对象,实例属性),也不需要使用类对象 (如类属性、类方法、创建实例等)时,定义静态方法取消不需要的参数传递,有利于减少不必要的内存占用和性能消耗1、通过实例定义的变量只能被实例方法访问2、而直接在类中定义的静态变量(如本例的xy变量)可以被实例方法访问,也可以被静态方法和类方法访问。3、实例方法不能被静态方法和类方法访问,但静态方法和类方法可以被实例方法访问。下面的代码,静态方法调用另一个静态方法,如果改用类方法调用静态方法,可以让cls代替类,让代码看起来精简一些。也防止类名修改了,不用在类定义中修改原来的类名。从下面代码可以看出,如果子类继承父类的方法,子类覆盖了父类的静态方法,子类的实例继承了父类的static_method静态方法,调用该方法,还是调用的父类的方法和类属性。子类的实例继承了父类的class_method类方法,调用该方法,调用的是子类的方法和子类的类属性。'''
class Zz(object):x=1 #静态变量y=2def __init__(self,a=3,b=4):self.a=aself.b=bdef aa(self):return self.a+self.b@staticmethoddef averag(*args):return sum(args)@staticmethoddef static_method():print('静态方法中调用静态方法')#return Zz.averag(Zz.a,Zz.b) #报错,未声明a,breturn Zz.x+Zz.y #只能使用类的参数,不能使用实例中定义的参数(对象的参数)@classmethoddef class_method(cls):print('在类方法中使用类方法')return cls.averag(cls.x,cls.y)# @staticmethod #报错,实例方法只能被对象访问# def static_method1():# return Zz.aa()class SonOfZz(Zz):x = 11y = 22@staticmethoddef averag(*args):print('子类的静态方法重载')return sum(args)/2.5f=Zz(11,22)
print(f.averag())
print(f.class_method())
print(f.static_method())
#print(f.static_method1())
print('====================')
s=SonOfZz()
print(s.static_method()) #子类的实例继承了父类的static_method静态方法,调用该方法,还是调用的父类的方法和类属性。
print(s.class_method()) #子类的实例继承了父类的class_method类方法,调用该方法,调用的是子类的方法和子类的类属性。
类对象的指针概念
'''类的对象有类指针概念,指向类(在python中,一切皆对象,类也是一种对象)'''
stu1.location='天津'
stu1.name='ling'
print(stu1.location) #对类里面的共享变量直接修改
print(stu1.name)
动态绑定属性,在类中直接添加新属性和新方法
stu1.gender='女' #动态绑定属性
def fun(a=0):print('我是一个函数',a)
stu1.fun=fun
stu1.fun()
- 面对对象的三个特性:
- 封装:将属性和方法封装到类对象中。在方法内部实现对属性的操作,在类对象的的外部调用方法。
这样,无需关心方法内部的具体实现细节,从而隔离了复杂度 - 继承:提高代码的复用性
- 多态:提高程序的可扩展性和可维护性
- 封装:将属性和方法封装到类对象中。在方法内部实现对属性的操作,在类对象的的外部调用方法。
class Car:def __init__(self,brand,macid):self.brand=brandself.__macid=macid #‘__’表示不希望在类的外部被使用(私有属性)def showmemac(self):print(self.__macid)
aodi=Car('奥迪', 4562531)
aodi.showmemac()
#print(aodi.macid) #报错,不可直接外部使用
print(dir(aodi))
print(aodi._Car__macid) #通过此方法也可访问私有属性
继承
单继承
#(支持多继承),如果一个类没有继承,默认继承object类,定义子类时,必须在其构造函数中调用父类的构造函数
class Person(object):def __init__(self,name,age):self.__name=nameself.age=agedef info_name(self):print(self.__name,end=' ')def info_oth(self):print(self.age,end=' ')def __str__(self):return '姓名:'+self.__name+' 年龄:'+str(self.age) #返回对象只能是一个,否则返回元组不是str类型,#用+返回时候需要对非str类型进行转换#或者用#return '姓名:{0},年龄:{1}'.format(self.__name,self.age)class Male(Person):def __init__(self,name,age,gender):super(Male, self).__init__(name,age)self.gender=genderdef pr_gen(self):print(self.gender)
#zhang_s=Male('zhangsan',21,'mals')
#zhang_f=Male('zhangba',51,'mals')
#print(zhang_f.name) #报错
#zhang_f.info()
#zhang_s.pr_gen()
多继承
class A(object):def __init__(self,a,d):self.a=aself.d=d
class B(object):def __init__(self,b):self.b=bclass C(A,B):def __init__(self,a,b,c,d):super(C, self).__init__(a,d) #效果等同于A.__init__(self,a)#super() 函数只可用于调用第一个父类的构造函数,其余父类的构造函数只能使用未绑定的方式调用B.__init__(self,b)self.c=cc_oj=C(1,2,3,4)
print(c_oj.a,c_oj.b,c_oj.c,c_oj.d)
#考虑到多层继承的问题,优先使用super()而不是使用未绑定的方法调用构造函数
‘’’
1.父类的非私有属性和非私有方法子类可以直接继承,子类对象可以直接使用。
如果子类要调用父类的私有属性和私有方法,只能通过间接的方法来获取。
2.子类可以实现父类没有的属性和方法,与继承的属性和方法互不干扰。
3.如果在子类中有跟父类同名的方法,但方法中执行的内容不同,则子类可以重写父类方法。
当子类实现一个和父类同名的方法时,叫做重写父类方法。直接在子类中定义与父类同名的方法,
然后在方法中实现子类的业务逻辑,子类方法就会覆盖父类的同名方法。子类重写了父类方法,
子类再调用该方法将不会执行父类的方法。
4.如果在子类重写父类的方法中,需要使用父类同名方法中的功能,在父类功能基础上做扩展,
则子类可以在重写的方法中调用父类被重写的方法,使用super()来调用。’’’
子类方法重写(1)
class Teacher(Person,object):def __init__(self, name, age,techyear):super(Teacher, self).__init__(name,age)self.techyear=techyeardef info_oth(self): #对此方法进行重写print(self.age,self.techyear)
子类方法重写(2)
class Officer(Person,object):def __init__(self, name, age,ofisyear):super(Officer, self).__init__(name,age)self.ofisyear=ofisyeardef info_oth(self): #对此方法进行重写,使用上述笔记中4的方法super(Officer, self).info_oth()print(self.ofisyear)t1=Teacher('wang',36,10)
t1.info_name()
t1.info_oth()of1=Officer('bai',56,20)
of1.info_name()
of1.info_oth()
object类
'''所有类的父类,所有类都有object的属性和方法内置函数dir()可以查看指定对象的所有属性object有一个__str__()方法,用于返回一个对于[对象的描述]对应于内置函数str()经常用于print()方法,帮我们查看对象的信息,所以我们经常会对__str__()进行重写
'''
print(of1) #对__str__()方法重写后可以很好用于输出
print('==========')
print(c_oj) #不重写,返回地址
print(dir(of1))
#多态性:即使不知道一个变量所引用的对象的类型,仍然可以通过这个变量调用方法,在运行过程中,根据对象的类型
# 动态决定调用哪个对象中的方法class Animal(object):def eat(self):print('动物需要能量')class Dog(Animal):def eat(self):print('狗吃骨头')class Human(Animal):def eat(self):print('人吃五谷')def fun(annimal):annimal.eat()def fun1(person):person.info_name()fun(Dog())
fun1(Teacher('ling',36,14)) #如果类需要初始化参数,必须给出,否则报错
print('')
fun1(Person('wang',16))
特殊方法和特殊属性
'''
特殊属性:_dict_:获得类对象或实例对象所绑定的所有属性和方法的字典
特殊方法:__len__():重写__len__()方法,让内置函数len()的参数可以是自定义类型__add__():重写__add__()方法,可以使用自定义对象具有的‘+’功能__new__():用于创建对象__init__():用于对创建对象进行初始化
'''
print(t1.__dict__) #查看实例对象所绑定的所有属性和方法
print(Student.__dict__) #查看类对象所绑定的所有属性和方法
print(of1.__class__) #输出对象所属的类
print(C.__base__) #父类类型的元素,优先输出第一个父类
print(C.__bases__) #所有父类类型的元素
print(C.__mro__) #类的层次结构
print(A.__subclasses__())#查看子类列表a=10
b=20
d=a.__add__(b) #等于a+b
print(d)class Name_class(object):def __init__(self,name,age):self.name=nameself.age=ageprint('init function called ,self id is:{0}'.format(id(self)))def __new__(cls, *args, **kwargs):print('new function called,id is :',id(cls))obj=super().__new__(cls)print('new object id is :{0}'.format(id(obj)))return objdef __add__(self, other):return self.name+other.namedef __len__(self):return len(self.name)n1=Name_class('张三',10)
n2=Name_class('李四',20)
print(n1+n2) #重新定义对象的加法运算
a=[11,22,33]
print(len(a)) #输出列表长度
print(len(n1)) #重写返回长度的方法
print('id of class:object is :{0}'.format(id(object)))
print('id of class:Name_class is :{0}'.format(id(Name_class)))
类的浅拷贝和深拷贝
- 浅拷贝
python一般是浅拷贝,拷贝时,对象包含的子对象内容不拷贝,因此源对象和拷贝对象会引用同一个同一个子对象 - 深拷贝
使用copy模块的deepcopy函数,递归拷贝对象中包含的子对象,源对象和拷贝对象的所有子对象也不相同
'''
变量的赋值操作只是形成两个变量,实际上还是指向同一个对象'''
class CPU(object):pass
class Disk:pass
class Computer:def __init__(self,cpu,disk):self.cpu=cpuself.disk=diskcpu1=CPU()
cpu2=cpu1 #浅拷贝
print(cpu1)
print(cpu2) #两者的id相同,两个不同的变量只是同一个对象(值)的引用
disk1=Disk()
computer1=Computer(cpu1,disk1)
import copy
computer2=copy.copy(computer1)
print(computer1,computer1.cpu,computer1.disk)
print(computer2,computer2.cpu,computer2.disk) #只有主对象进行了拷贝,子对象的空间还是一样的
computer3=copy.deepcopy(computer1)
print(computer3,computer3.cpu,computer3.disk) #子对象也拷贝了
模块
import calc
#如果报错,在目录中单击邮件,make directory as -source root
#创建一个模块:.py文件,名称不要和python自带的标准模块名称相同
#导入方式:import 模块名称 【as 别名】
# from 模块名称 import 函数/变量/类
#以主程序形式运行,每一个模块的定义中都包括一个记录模块名称的变量__name__,程序可以检测该变量,以
#确定他们在哪个模块中执行。如果一个模块不是被导入到其他程序中执行,那么他可能在解释器的顶级模块中执行
顶级模块__name__变量的值为__mian__
if __name__ == '__main__': #main回车print(calc.add(20,10))
print('===================')
python的包
- 分层次的目录结构,将一组功能相近的模块组织在一个目录下
- 包的作用:代码规范,避免模块名称冲突
- 包和目录的区别:包含__init__.py文件的目录成为包,目录里通常不包含__init__.py文件
- 包的导入:import 包名.模块名
创建
- 创建一个新的文件夹new-python package,文件夹内部有__init__.py文件的叫包,否则叫目录
目录创建
- new -> Derictory
import package1.moduleB as jsq #jsq就是这个模块的别名,使得代码更加简短
print(jsq.add(10,100))
导入包的注意事项
# 使用import导入,只能跟包名或者模块名
# from。。 import。。导入可以导入包,模块,变量
'''python中常用的内置模块sys 与python解释器及其环境操作相关的标准库time 提供与时间相关的各种函数的标准库os 提供了访问操作系统服务功能的标准库calendar 提供与日期相关的各种函数的标准库urllib 用于读取来自网上(服务器)的数据标准库(包)json 用于使用json序列化和反序列化对象re 用于字符串中执行正则表达式匹配和替换math 提供标准算术运算函数的标准库decimal 用于进行精确控制运算精度、有效数位和四舍五入操作的十进制运算logging 提供了灵活记录事件、错误、警告和调试信息等日志信息功能
'''
查看包的所有信息
- 按住CTRL点开模块
模块安装位置
- 找到语句:exec_prefix =
urllib包中的request模块
import urllib.request as req
print(req.urlopen('http://www.baidu.com').read())import schedule
import time
def job():print('haha')schedule.every(3).seconds.do(job) #每隔3秒执行一次函数
while True:schedule.run_pending()
time.sleep(1)
【在另一个calc.py文件中】
# -*- coding:utf-8 -*- def add(a,b):return a+bdef div(a,b): return a/b
【在另一个package1.moduleA模块中】
# -*- coding:utf-8 -*- def add(a,b):return a+bdef div(a,b): return a/b
编码格式和文件读写
编码格式:乱码问题
- python的解释器使用的是Unicode(内存)
- py文件在磁盘中使用UTF-8存储(外存)
修改编码格式
- 在开头语句中加入’#encoding=gbk’
编码格式决定文件大小
文件读写原理:io操作
- 操作流程:python操作文件、打开或新建文件、读写操作、关闭资源
- 打开文件:file=open(filename [,mode(打开模式:读/写,默认只读),encoding(默认编码格式位gbk)])
- readlines()返回列表
文件打开方式
with语句:自动调用enter和exit特殊方法
自动管理上下文资源,不论什么原因跳出with块,都能确保文件正确关闭,以此来达到释放资源的目的,无论过程是否报错
with open('a.txt','r') as file:print(file.read())
MyContentMgr实现了特殊方法enter和exit成为该类对象遵守了上下文管理器协议
该类对象的实例对象被成为上下文管理器class MyContentMgr(object):def __enter__(self):print('enter方法被调用执行')return selfdef __exit__(self, exc_type, exc_val, exc_tb):print('exit方法被调用执行')def show(self):print('show方法被调用执行')
目录操作
- os模块是python的内置的与操作系统功能和文件系统相关的模块
该模块中语句的执行结果通常与操作系统有关,在不同操作系统中运行,得到的结果不一样 - os模块和os.path模块用于对目录或文件进行操作
其他包的使用请看高级应用篇
python入门笔记(掌握一门语言的四分之一)相关推荐
- python入门笔记——内置函数作业
python入门笔记--内置函数作业 # 求三组连续自然数的和:求出1到10,20到30,35到45的三个和 sum1 = sum(range(1,11)) sum2 = sum(range(20,3 ...
- python入门笔记之初步了解代码
# # python入门笔记之初步了解代码 #### 昨日回顾 ##### 操作系统 对计算机:秘书,管家 对人类:提供一个人性化操作台 ##### 三层架构 ```mermaid graph TD ...
- python入门笔记——飞机大战(极简版、未进行继承优化)
python入门笔记--飞机大战(极简版.未进行继承优化) import random import pygame# 引用pygame里的模块 from pygame.locals import *# ...
- python入门笔记——类和对象⑤(继承)
python入门笔记--类和对象⑤(继承) # python中展现面向对象的三大特征:封装.继承.多态 # 封装:把内容封装到某个地方以便后续的使用 # 对封装来说,其实就是使用初始化构造方法将内容封 ...
- Python 入门笔记6——列表
Python 入门笔记6--列表 序列 列表 列表的创建 list()创建 range()创建整数列表 推导式生成列表 列表元素的增加 append()方法 +运算符操作 +=运算符操作 extend ...
- 编程入门python java和c语言_学习编程适不适合从Python入门?哪种语言更适合入门?...
本文对比了C语言和Python语言,分析它们作为编程入门语言各自的利弊,并给出了我推荐的编程学习道路. 我本身已经入门了Python脚本语言,在进阶C语言和JAVA语言后,Python重学就轻松很多, ...
- Python入门笔记,看完直接玩几个小案例是没有问题滴~
这篇是纯干货分享,对python感兴趣的可以认真看起来! 小白想要入门Python爬虫,首先得了解爬虫的基本工作原理和相关的理论基础,爬虫简介部分就不细说了,都可以百度得到. 爬虫工作原理总结来讲就是 ...
- 2020最新Python入门笔记,建议收藏
Python变量和数据类型 数据类型 print语句 注释 Python的注释以 # 开头,后面的文字直到行尾都算注释 # 这一行全部都是注释... print 'hello' # 这也是注释 这里要 ...
- python新手入门笔记_2020最新Python入门笔记
Python变量和数据类型 数据类型 print语句 注释 Python的注释以 # 开头,后面的文字直到行尾都算注释 这里要注意注意:不管你是为了Python就业还是兴趣爱好,记住:项目开发经验永远 ...
最新文章
- 2、计算机图形学——3D变换
- android中解压文件
- 文巾解题 1744. 你能在你最喜欢的那天吃到你最喜欢的糖果吗?
- fortify安装_Rjava的安装
- 罗斯蒙特电磁流量计8723说明书_罗斯蒙特8732E电磁流量计故障原因及解决办法!...
- mysql5.7物理备份_Mysql5.7—运维常用备份方式
- 随想录(串级PID的学习)
- bgll算法 matlab,一种复杂网络社区检测的方法与流程
- 书单丨成为全栈工程师的5种硬实力
- 拓端tecdat|R语言使用bootstrap和增量法计算广义线性模型(GLM)预测置信区间
- 每周个人进度总结06
- redux-chunk中间件的安装和使用-(二)
- Android友盟分享7.1.5版本巨坑
- 写贺卡给毕业师姐怎么写计算机系的,给师兄师姐的毕业贺卡寄语
- embed实现PDF文件预览
- 北京冬奥会使用的集装箱最后如何处理
- mongodb获取具体某一天的查询语句
- JavaWeb 修炼之路(五)服务器中的请求和响应
- RISC-V SiFiveU64内核——L2 Prefetcher预期器
- win11右键直接显示更多选项
热门文章
- 基于Android平台移动社交网络
- Opencv 使用Rect选取与设置窗口ROI
- ArcGIS基础实验操作100例--实验28地形图配准
- 110、了解哪些前端的新技术
- 京东便利店拿什么保障百万便利店的服务品质,刘强东是这样说的
- 一、文本框和按钮不对齐现象(高度得设置一样)
- 【微语】第三周(11.30~12.06)
- 【Python】用Python检测电脑状态信息
- ApacheCN 翻译/校对活动进度公告 2022.5.4
- v80八核 android6,高通发布骁龙810八核/808六核64位芯片