你们的三连(点赞,收藏,评论)是我持续输出的动力,感谢。
在兴趣中学习,效益超乎想象,①有趣的源码与学习经验,②工具安装包,③专业解答,④学习资料共享
点击领取福利
PyCharm 是一种 PythonIDE,附带一辈可以帮助用户在使用 Python 语言开发时提高其效率的工具,例如调试、语法高亮、项目管理、代码跳转、智能提示、自动完成、单元测试、版本控制。此外,该IDE提供了一些高级功能,用于支持Django框架下的专业Web开发。
使用pycharm写出第一个程序
1)打开 Pycharm,选择Create New Project
,创建一个新项目创建项目
2)选择Pure Python
表示创建一个纯 Python 程序项目,Location
表示该项目保存的路径,Project Interpreter
表示使用的 Python 解释器版本,最后点击Create
创建项目。创建文件第二步
3)右击项目,选择New
,再选择Python File
创建文件第三步
4)在OK
创建一个文本的文本对话框中输入的文件名Hello,点击,显示Python程序的文本文件文件后缀名默认.py创建文件第四步
5)输入以下代码,并右击空白处,选择Run
运行,表示打印一个字符串“Hello World!”。
print(“Hello World!”)
6)运行成功后,Pycharm Console 窗口将显示我们的输出结果。
通过用自己的语言,在对部分代码进行认知说明,这就是语音的作用,能够放大膨胀程序的神话性
单行注释:
以#开头,#右边的所有东西当做说明,而不是真正要执行的程序,起辅助说明作用
#这是python代码的注释
print ( "hello world" )
多行注释:
以""""""包裹或者’’’’’’'包裹,包裹中的内容就是注释部分
'''这是多行注释'''
"""这也是多行注释"""
注意
多行对方的符号,必须一样不能要么都是单引号,要么都是单引号,不能混用
1)什么是变量?
变量是事件数据值的,程序就是处理数据的,而变量就是存储数据的
2)数据类型
为了更充分地利用内存空间以及不断的管理内存,变量是有不同的类型的。
3)有哪些变量的类型呢?
在python中,只要定义了一个变量,它就有数据,那么它的类型就已经确定了,不需要我们开发者主动去说明它的类型,系统会自动气泡
可以使用type(变量的名字),来查看变量的类型
在 Python 中的数有四种,分别是整数(int)、长整数(long)、浮点数(float)、复数(complex)。
像 6 这样的数字就是整数,不带小数点的,而长整数只不过代表的是比较大一点的整数,现在 python3 中的整数(int)已经不限制数的大小限制了,所以整数类型也包括长整数。
我们可以通过 Python 交互式解释器来运算整数:
这里的 「6+6」没什么好说的吧,而 「6//2」就是6整除2的意思了,「1%2」的意思是说1除以2的余数,「%」有个专业名词叫做取余或者取模。而「2**3」就是2的三次方的意思。
但是如果你试试 「1/2」,这时候你会发现结果有小数点:
在这里的 「/」是除的意思,但是不会整除,你可以看到每次的结果都会有小数点。而这些像 「0.5」,「1.0」带有小数点的数我们就叫做浮点数。
Python中的复数由实数部分和虚数部分组成。虚部的后缀为「j」。
例如:4+5j 就是一个复数,实数部分为 4.0,虚数部分为 5.0。
你可以把复数理解成为一个平面的一个点,例如上面这个例子你可以把它理解为平面上的点(4,5)。
我们小时候,老师都教过我们 1+1=2 ,这个 「1+1」 就是表达式, 「+」 就是运算符。
咱们接下来就来了解一下,在 python 中,那些运算符是什么意思,怎么用? 相信看完,你就能够明白了。
对于 ±*/ 我们都知道它们是什么含义了吧,就算你的数学是体育老师教的,你也会懂加减乘除吧。
不过有两个小细节值得你去注意,就是字符串之间的相加和相乘:
字符串之间的相加会被"拼接"起来,而字符串和数字相乘就会重复多次相同的字符串。
其它的大于、小于、大于等于、小于等于就不说了,因为我们小学老师都跟我们说过了。接下来说几个比较少见的符号。
幂就是以前我们学数学的时候老师讲的什么什么几次方,别一看到幂就想到杨幂。
用符号 **
表示, 比如 2**3 = 8
。
我们知道 /
是除的意思,你知道 6/3 等于多少么?你可能会觉得在侮辱你的智商对不对,不是 2 么? 在 python 中得出的结果是 2.0 , 也就是它返回的是浮点数。 那么我们只想得到整数部分怎么玩呢?
用 //
这个 : 6//3 = 2
取模的意思不是让你去获取个模特,是得到除法的余数,比如 8%5 = 3
,因为 8/5 = 1余3
。
移的意思就是把一个数的二进制移动多少个位。
比如 2 << 2 = 8 。
首先 2 的 二进制 是 0b00000010 ,然后将它左移2位(虚位补0)就变成这样: 0b00001000 ,它对应的十进制就是 8 。
同样的道理:
8 >> 2 的意思就是将 8 的二进制向右移动2位:
0b00001000 右移动2位:0b00000010 也就是对应十进制的 2。
那么下次有人问你2*8怎么样写代码比较高效,你就直接甩给它: 2<<3 就好了。
记住一句话:“同真与真”,什么意思呢? 比如 1&1=1,1&0=0,
1就是真,0就是假。也就是只有 1&1=1,其它的都等于0。
那么 2 & 3 怎么算?
先将它们转化为二进制:
2对应的二进制 : 0b00000010
3对应的二进制 : 0b00000011
那么从右往左: 0&1=0 ,1&1=1,0&0=0,所以结果为
0b00000010,转化为十进制就是2,所以 2&3=2。
记住一句话:“同假或假”,什么意思呢? 比如 1|1=1,0|0=0,
1就是真,0就是假。也就是只有 0|0=0,其它的都等于1。
那么 2 | 3 怎么算?
先将它们转化为二进制:
2对应的二进制 : 0b00000010
3对应的二进制 : 0b00000011
那么从右往左: 0|1=1 ,1&1=1,0&0=0,所以结果为
0b00000011,转化为十进制就是3,所以 2|3=3。
相同者假,不同者真,什么意思呢?就是 1^1=0, 1^0=1。
那么 2^3 怎么算?
先将它们转化为二进制:
2对应的二进制 : 0b00000010
3对应的二进制 : 0b00000011
那么从右往左: 0^1=1 ,1^1=0,0&0=0,所以结果为
0b00000001,转化为十进制就是1,所以 2^3=1。
x的按位翻转就是是-(x+1)。
那么 ~2 怎么算?
~2 = -(2+1) ; 所以答案就是-3。
ok,以上,其实没必要去记住,了解一下就这些符号是什么意思,怎么算的就好了。
while 活着:
每天做着一样的事情。
这样写的意思就是,只要你活着,就一直不断的执行while下面的语句。
我们可以来写一个抛硬币的 python 程序,我们事先定义好硬币的正反面,然后让用户猜,如果用户猜对了就奖励一个吻,猜错了就继续猜,直到让他猜中为止。打开我们的 IDLE,代码敲起来:
首先定义一个变量,我们的值定义为正面:
coin = "正面"
接着定义一个 flag :
flag = True
然后我们写一个循环:
while flag :
guess = input("请猜一下是正面还是反面:")
if(guess == "反面") :
print("你猜错了,继续猜")
elif(guess == "正面") :
print("恭喜你猜对了,奖励你一个吻")
flag = False
执行:
解释一下:当 while 发现 flag 为 true 的时候,就会一次又一次的执行执行 while 下面的一句,直到我们猜中之后,我们就将flag 这个变量改为 false ,while 发现为 false 的时候就不往下循环了。
1.计算1~100的累积和(包含1和100)
i = 1
sum = 0
while i <= 100:
sum += i
i+=1
print(sum)
结果:
5050
while 可以做到在条件为真的时候反复的执行,不过有时候我们需要在特定范围循环,比如说我们要在第一天到第五天每天做运动一次,那么这时候用 for 就再适合不过了:
days = [1,2,3,4,5]
for day in days :
print("第" + str(day) + "天做运动")
day就是1,第二次day就是2,它就这样一直循环下去,没有一点念想。
有一天你突然发现,我不能再这么下去了,不能再重复的过这样的日子了,得有点改变,跳出这个重复的怪圈,那么对于 Python 来说,用break:
while 活着:
重复的过日子。
if(醒悟):
break
通过 break 呢,就可以跳出这个循环了。
break 会立即终止循环,跳转到循环之后开始执行
结构:
while 条件:
if 条件:
break # 跳出循环
举例:
i = 10
while i > 0:
print("妈,还要我刷啊~~~~~~~~~")
if i == 5:
print('好了,不用刷了')
break
print("正在刷 %d 个碗" % i)
i -= 1
print('程序结束')
运行结果:
妈,还要我刷啊~~~~~~~~~
正在刷 10 个碗
妈,还要我刷啊~~~~~~~~~
正在刷 9 个碗
妈,还要我刷啊~~~~~~~~~
正在刷 8 个碗
妈,还要我刷啊~~~~~~~~~
正在刷 7 个碗
妈,还要我刷啊~~~~~~~~~
正在刷 6 个碗
妈,还要我刷啊~~~~~~~~~
好了,不用刷了
程序结束
continue 会立即结束当前这一次循环,跳转到下一轮循环的条件判断
结构:
i = 10
while i > 0:
print("妈,还要我刷啊~~~~~~~~~")
if i == 5:
print('好了,不用刷了')
i -= 1 # continue 之前要注意修改 i 的值,否则容易导致死循环
continue
print("正在刷 %d 个碗" % i)
i -= 1
print('程序结束')
运行结果:
妈,还要我刷啊~~~~~~~~~
正在刷 10 个碗
妈,还要我刷啊~~~~~~~~~
正在刷 9 个碗
妈,还要我刷啊~~~~~~~~~
正在刷 8 个碗
妈,还要我刷啊~~~~~~~~~
正在刷 7 个碗
妈,还要我刷啊~~~~~~~~~
正在刷 6 个碗
妈,还要我刷啊~~~~~~~~~
好了,不用刷了
妈,还要我刷啊~~~~~~~~~
正在刷 4 个碗
妈,还要我刷啊~~~~~~~~~
正在刷 3 个碗
妈,还要我刷啊~~~~~~~~~
正在刷 2 个碗
妈,还要我刷啊~~~~~~~~~
正在刷 1 个碗
程序结束
注意点:
举例:
>>> # int(): 将数据转换为 int 类型
...
>>> str1 = "10"
>>> # int() 默认按10进制转换后显示
... num1 = int(str1)
>>>
>>> # int() 处理浮点数,只留下整数部分,舍弃小数部分(并不是四舍五入操作)
... num2 = int(3.74)
>>> print(num2)
3
>>>
>>> """
... num1 = int(str1, 8) # 第二个参数为8,表示按8进制转换后显示,结果为 8
... num1 = int(str1, 16) # # 第二个参数为16,表示按16进制转换后显示,结果为 16
... #01 02 03 04 05 06 07 10
... #01 02 ... 0B 0C 0D 0E 0F 10
... print(num1)
... """
>>>
>>> # float() 将数据转化为浮点数
... str2 = "3.14"
>>> f1 = float(str2)
>>> print(type(f1))
<class 'float'>
>>>
>>> f2 = float(10)
>>> print(f2)
10.0
>>>
>>> # complex() 创建复数: 第一个参数是复数的实部,第二个参数是复数的虚部
... c1 = 10 + 4j
>>> c2 = complex(10, 4)
>>>
>>> print(c1)
(10+4j)
>>> print(c2) # 等同与c1
(10+4j)
>>>
>>> # str() : 转换为 字符串类型
... num1 = 10
>>> f1 = 3.14
>>>
>>> print(type(str(num1)))
<class 'str'>
>>> print(type(str(f1)))
<class 'str'>
>>>
>>> # repr(): 转换为表达式字符串
... num1 = 10
>>> print(type(repr(num1)))
<class 'str'>
>>>
>>>
>>> # eval(): 将字符串形式的数据,转换为原本的类型
... str1 = "3.14"
>>> print(type(eval(str1)))
<class 'float'>
>>>
>>> str2 = "[10, 20, 30]"
>>> l = eval(str2)
>>> print(type(l))
<class 'list'>
>>>
>>>
>>> # chr: 将一个整数转换为对应的 Unicode 字符
... s = chr(1065)
>>> print(s)
Щ
>>>
>>> # ord :将一个字符转换为对应的字符编码数字
... n = ord("A")
>>> print(n)
65
>>>
>>> # bin: 将一个整数转换为二进制
... print(bin(1024)) # 0b 开头表示二进制数
0b10000000000
>>>
>>> # oct:将一个整数转换为八进制
... print(oct(1024)) # 0o 开头表示八进制数
0o2000
>>>
>>> # hex: 将一个整数转换为十六进制
... print(hex(1024)) # 0x 开头表示十六进制
0x400
>>>
附录:常用字符与ASCII码对照表
1)什么是列表?
列表是用来存储大量数据的容器
2)列表的格式
[value1,value2,value3,...]
注意:python列表中存储的数据可以是不同的数据类型
结构:
mylist.append(values)
举例:
#定义变量A,默认有3个元素
A = ['xiaoWang','xiaoZhang','xiaoHua']
print("-----添加之前,列表A的数据-----")
for tempName in A:
print(tempName)
#提示、并添加元素
temp = input('请输入要添加的学生姓名:')
A.append(temp)
print("-----添加之后,列表A的数据-----")
for tempName in A:
print(tempName)
运行结果
-----添加之前,列表A的数据-----
xiaoWang
xiaoZhang
xiaoHua
请输入要添加的学生姓名:哈哈
-----添加之后,列表A的数据-----
xiaoWang
xiaoZhang
xiaoHua
哈哈
结构:
mylist.insert(index, object) 在指定位置index前插入元素object
举例:
>>> a = [0, 1, 2]
>>> a.insert(1, 3)
>>> a
[0, 3, 1, 2]
extend(通过extend可以将另一个集合中的元素逐一添加到列表中)
结构:
myslist.extend(index,list)在指定位置index前插入列表
举例:
>>> a = [1, 2]
>>> b = [3, 4]
>>> a.append(b)
>>> a
[1, 2, [3, 4]]
>>> a.extend(b)
>>> a
[1, 2, [3, 4], 3, 4]
结构:
del mylist(index) # 删除mylist中index位置的元素
举例:
movieName = ['加勒比海盗','骇客帝国','第一滴血','指环王','霍比特人','速度与激情']
print('------删除之前------')
for tempName in movieName:
print(tempName)
del movieName[2]
print('------删除之后------')
for tempName in movieName:
print(tempName)
运行结果:
------删除之前------
加勒比海盗
骇客帝国
第一滴血
指环王
霍比特人
速度与激情
------删除之后------
加勒比海盗
骇客帝国
指环王
霍比特人
速度与激情
结构:
list.pop()
举例:
movieName = ['加勒比海盗','骇客帝国','第一滴血','指环王','霍比特人','速度与激情']
print('------删除之前------')
for tempName in movieName:
print(tempName)
movieName.pop()
print('------删除之后------')
for tempName in movieName:
print(tempName)
运行结果:
------删除之前------
加勒比海盗
骇客帝国
第一滴血
指环王
霍比特人
速度与激情
------删除之后------
加勒比海盗
骇客帝国
第一滴血
指环王
霍比特人
结构:
mylist.remove(value) # value 是mylist中的值
举例:
movieName = ['加勒比海盗','骇客帝国','第一滴血','指环王','霍比特人','速度与激情']
print('------删除之前------')
for tempName in movieName:
print(tempName)
movieName.remove('指环王')
print('------删除之后------')
for tempName in movieName:
print(tempName)
运行结果:
------删除之前------
加勒比海盗
骇客帝国
第一滴血
指环王
霍比特人
速度与激情
------删除之后------
加勒比海盗
骇客帝国
第一滴血
霍比特人
速度与激情
修改元素的时候,要通过下标来确定要修改的是哪个元素,然后才能进行修改
结构:
mylist[index] = newValue
举例:
# 定义变量A,默认有3个元素
A = ['xiaoWang', 'xiaoZhang', 'xiaoHua']
print("-----修改之前,列表A的数据-----")
for tempName in A:
print(tempName)
# 修改元素
A[1] = 'xiaoLu'
print("-----修改之后,列表A的数据-----")
for tempName in A:
print(tempName)
运行结果:
-----修改之前,列表A的数据-----
xiaoWang
xiaoZhang
xiaoHua
-----修改之后,列表A的数据-----
xiaoWang
xiaoLu
xiaoHua
python中查找的常用方法为:
例如:
#待查找的列表
nameList = ['xiaoWang','xiaoZhang','xiaoHua']
#获取用户要查找的名字
findName = input('请输入要查找的姓名:')
#查找是否存在
if findName in nameList:
print('在字典中找到了相同的名字')
else:
print('没有找到')
运行结果1:(找到)
请输入要查找的姓名:xiaoWang
在字典中找到了相同的名字
运行结果2:(没有找到)
请输入要查找的姓名:xiaoli
没有找到
说明:
in的方法只要会用了,那么not in也是同样的用法,只不过not in判断的是不存在
index和count与字符串中的用法相同
>>> a = ['a', 'b', 'c', 'a', 'b']
>>> a.index('a', 1, 3) # 注意是左闭右开区间
Traceback (most recent call last):
File "" , line 1, in <module>
ValueError: 'a' is not in list
>>> a.index('a', 1, 4)
3
>>> a.count('b')
2
>>> a.count('d')
0
其实元组和列表是差不多的,不过它们有一点区别就是:元组是不可变的数据类型,也就是说元组里面的内容是不能进行修改,删除,添加等操作的。
元组使用圆括号来表示,例如:avlist = ('亚洲无码原创区' ,'亚洲有码原创区' ,'欧美原创区' ,'动漫原创区' )
元组通常被用来打印语句:
举例:
mylist = ('123',1,"hhh")
print(mylist[0])
运行结果:
'123'
例如:
mylist = ('123',1,"hhh")
mylist[0] = "lisi"
print(mylist)
运行结果:
('lisi',1,'hhh')
index和count与字符串和列表中的用法相同
>>> a = ('a', 'b', 'c', 'a', 'b')
>>> a.index('a', 1, 3) # 注意是左闭右开区间
Traceback (most recent call last):
File "" , line 1, in <module>
ValueError: tuple.index(x): x not in tuple
>>> a.index('a', 1, 4)
3
>>> a.count('b')
2
>>> a.count('d')
0
1)字符串介绍
被一对双引号或者单引号包裹的数据就是字符串
2)字符串输入
之前在学习input的时候,通过它能够完成从键盘获取数据,然后保存到指定的变量中;
注意:input获取的数据,都以字符串的方式进行保存,即使输入的是数字,那么也是以字符串方式保存
下标/索引
“下标
”又叫“索引
”,就是编号。
字符串中"下标"的使用
如果有字符串:name = 'abcdef'
,在内存中的实际存储如下:
如果想取出部分字符,那么可以通过下标的方法,(注意python中下标从 0 开始)
name = 'abcdef'
print(name[0])
print(name[1])
print(name[2])
运行结果:
a
b
c
切片是指对操作的对象截取其中一部分的操作。字符串、列表、元组都支持切片操作。
切片的语法:[起始:结束:步长]
注意:选取的区间从"起始"位开始,到"结束"位的前一位结束(不包含结束位本身),步长表示选取间隔。
我们以字符串为例讲解。
如果取出一部分,则可以在中括号[]中,使用:
name = 'abcdef'
print(name[0:3]) # 取 下标0~2 的字符
abc
由键-值对组成的数据
结构:
{
key:value}
说明:
如果在使用 变量名[‘键’] = 数据 时,这个“键”在字典中,不存在,那么就会新增这个元素
举例:
info = {
'name':'班长', 'sex':'f', 'address':'地球亚洲中国北京'}
# print('id为:%d'%info['id'])#程序会终端运行,因为访问了不存在的键
newId = int(input('请输入新的学号'))
info['id'] = newId
print('添加之后的id为:%d'%info['id'])
运行结果:
请输入新的学号188
添加之后的id为: 188
del 删除指定的元素
结构:
del mydic[key]
例子:
info = {
'name':'班长', 'sex':'f', 'address':'地球亚洲中国北京'}
print('删除前,%s'%info['name'])
del info['name']
print('删除后,%s'%info['name']) ## 删除后不能访问会报错
运行结果:
KeyError: 'name'
删除前,班长
clear() 清空整个字典
结构:
mydic.clear()
demo:
info = {
'name':'monitor', 'sex':'f', 'address':'China'}
print('清空前,%s'%info)
info.clear()
print('清空后,%s'%info)
运行结果:
{
}
字典的每个元素中的数据是可以修改的,只要通过key找到,即可修改
例子:
info = {
'name':'班长', 'id':100, 'sex':'f', 'address':'地球亚洲中国北京'}
newId = input('请输入新的学号')
info['id'] = int(newId)
print('修改之后的id为:%d'%info['id'])
运行结果:
请输入新的学号12
修改之后的id为:12
除了使用key查找数据,还可以使用get来获取数据
结构
mydict[key] # 方法一
mydict.get(key)
例子:
info = {
'name':'吴彦祖','age':18}
print(info['age']) # 获取年龄
# print(info['sex']) # 获取不存在的key,会发生异常
print(info.get('sex')) # 获取不存在的key,获取到空的内容,不会出现异常
运行结果:
18
None
如果在开发程序时,需要某块代码多次,但是为了提高编写的效率以及代码的重用,所以把具有独立功能的代码块组织为一个小模块,这就是函数
函数定义
定义函数的结构:
def 函数名:
代码
举例:
# 定义一个函数,能够完成打印信息的功能
def printInfo():
print('------------------------------------')
print(' 人生苦短,我用Python')
print('------------------------------------')
调用函数
定义了函数之后,就相当于有了一个具有某些功能的代码,想要让这些代码能够执行,
调用函数的结构
函数名()
举例:
# 定义完函数后,函数是不会自动执行的,需要调用它才可以
printInfo()
>>> def test(a,b):
... "用来完成对2个数求和"
... print("%d"%(a+b))
...
>>>
>>> test(11,22)
33
如果执行,以下代码
>>> help(test)
能够看到test函数的相关说明
Help on function test in module __main__:
test(a, b)
用来完成对2个数求和
(END)
小结:
在函数定义之后在函数定义后的那行添加上对函数的注释,使用help函数就可以直接打印函数的注释和函数名
所谓函数的参数就是在定义函数的时候可以让函数接收数据
结构:
def 函数名(参数名):
代码(代码中可以使用参数)
举例:
def add2num(a, b):
c = a+b
print(c)
结构1:
函数名(参数名=数据)
结构2:
函数名(数据) # 必须是参数名有几个数据就有几个,且位置对应
举例:
add2num(a=1,b=2)
# add2num(1,2)
>>> def test(a,b):
... print(a,b)
...
>>> test(1,2)
1 2
>>> test(b=1,a=2)
2 1
>>>
>>> test(b=1,2)
File "" , line 1
SyntaxError: positional argument follows keyword argument
>>>
>>>
调用函数时,缺省参数的值如果没有传入,则取默认值
def printinfo(name, age=35):
# 打印任何传入的字符串
print("name: %s" % name)
print("age %d" % age)
# 调用printinfo函数
printinfo(name="miki") # 在函数执行过程中 age去默认值35
printinfo(age=9 ,name="miki")
运行结果:
name:miki age:35
name:miki age:9
总结:
基本语法:
def 函数名(形参,\*形参,\**形参):
执行功能
return 返回值
def fun(a, b, *args, **kwargs):
"""可变参数演示示例"""
print("a =%d" % a)
print("b =%d" % b)
print("args:")
print(args)
print("kwargs: ")
for key, value in kwargs.items(): #遍历字典
print("key=%s" % value) #输出字典
fun(1,2,3,4,5,m=6,n=7,p=8)#调用函数
运行结果:
a = 1 b = 2 args = [3,4,5] kwargs = {
"m":6,"n":7,"p":8}
注意:
1)缺省参数
结构:
def 函数名(参数名称=值): # 参数名称=值这种就是缺省参数
代码
举例:
def printinfo(name, age=35):
# 打印任何传入的字符串
print("name: %s" % name)
print("age %d" % age)
# 调用printinfo函数
printinfo(name="miki") # 在函数执行过程中 age去默认值35
printinfo(age=9 ,name="miki")
运行结果:
name: miki
age: 35
name: miki
age: 9
2)不定长参数
结构:
def 函数名([formal_args,] *args, **kwargs): # *args, **kwargs就是不定长参数
"""函数_文档字符串"""
代码
return [expression]
意义:有时可能需要一个函数能处理比当初声明时更多的参数, 这些参数叫做不定长参数,声明时不会命名。
注意:
作用:可以接受不定的数据
举例:
def func(a, b, *args, **kwargs):
"""可变参数演示示例"""
print("a=%s" % a)
print("b=%s" % b)
print("args:", end="")
print(args)
print("kwargs:", end="")
for key, value in kwargs.items():
print("key=%s," % key, end="")
print("value=%s" % value, end="\n")
# 注意参数对应
func(1, 2, 3, 4, 5, m=6, n=7, p=8)
print("---------------------------")
c = (3, 4, 5)
d = {
"m": 6, "n": 7, "p": 8}
# 注意元组和字典的传参方式
func(1, 2, *c, **d)
print("---------------------------")
# 不加*比较
func(1, 2, c, d)
运行结果:
a=1
b=2
args:(3, 4, 5)
kwargs:key=m,value=6
key=n,value=7
key=p,value=8
---------------------------
a=1
b=2
args:(3, 4, 5)
kwargs:key=m,value=6
key=n,value=7
key=p,value=8
---------------------------
a=1
b=2
args:((3, 4, 5), {
'm': 6, 'n': 7, 'p': 8})
kwargs:
3)缺省参数在*args后
如果很多个值都是不定长参数,那么这种情况下,可以将缺省参数放到 *args的后面, 但如果有**kwargs的话,**kwargs必须是最后的
例子:
def sum_nums_3(a, *args, b=22, c=33, **kwargs):
print(a)
print(b)
print(c)
print(args)
print(kwargs)
sum_nums_3(100, 200, 300, 400, 500, 600, 700, b=1, c=2, mm=800, nn=900)
运行结果:
100
1
2
(200, 300, 400, 500, 600, 700)
{
'mm': 800, 'nn': 900}
所谓“返回值”,就是程序中函数完成一件事情后,最后给调用者的结果
**1)**带有返回值的函数
结构:
def 函数名(参数名/无参数名):
“”“注释”“”
代码
return 返回值
举例:
def add2num(a, b):
c = a+b
return c
所谓的保存其实就是将返回值给予给一个新的变量
举例:
#定义函数
def add2num(a, b):
return a+b
#调用函数,顺便保存函数的返回值
result = add2num(100,98)
#因为result已经保存了add2num的返回值,所以接下来就可以使用了
print(result)
结果:
198
关于return:一个函数中可以有多个return语句,但是只要有一个return语句被执行到,那么这个函数就会结束了,因此后面的return没有什么用处
返回多值的方法:return后面可以是元组,列表、字典等,只要是能够存储多个数据的类型,就可以一次性返回多个数据
注意:
return后面有多个数据,那么默认是元组
例如:
def divid(a, b):
shang = a//b
yushu = a%b
return shang, yushu #默认是元组
result = divid(5, 2)
print(result) # 输出(2, 1)
函数根据有没有参数,有没有返回值,可以相互组合,一共有4种
此类函数,不能接收参数,也没有返回值,一般情况下,打印提示灯类似的功能,使用这类的函数
def printMenu():
print('--------------------------')
print(' xx涮涮锅 点菜系统')
print('')
print(' 1. 羊肉涮涮锅')
print(' 2. 牛肉涮涮锅')
print(' 3. 猪肉涮涮锅')
print('--------------------------')
结果:
--------------------------
xx涮涮锅 点菜系统
1. 羊肉涮涮锅
2. 牛肉涮涮锅
3. 猪肉涮涮锅
--------------------------
此类函数,不能接收参数,但是可以返回某个数据,一般情况下,像采集数据,用此类函数
# 获取温度
def getTemperature():
# 这里是获取温度的一些处理过程
# 为了简单起见,先模拟返回一个数据
return 24
temperature = getTemperature()
print('当前的温度为:%d'%temperature)
结果:
当前的温度为: 24
此类函数,能接收参数,但不可以返回数据,一般情况下,对某些变量设置数据而不需结果时,用此类函数
此类函数,不仅能接收参数,还可以返回某个数据,一般情况下,像数据处理并需要结果的应用,用此类函数
# 计算1~num的累积和
def calculateNum(num):
result = 0
i = 1
while i<=num:
result = result + i
i+=1
return result
result = calculateNum(100)
print('1~100的累积和为:%d'%result)
结果:
1~100的累积和为: 5050
5.小总结
def testB():
print('---- testB start----')
print('这里是testB函数执行的代码...(省略)...')
print('---- testB end----')
def testA():
print('---- testA start----')
testB()
print('---- testA end----')
testA()
结果:
---- testA start----
---- testB start----
这里是testB函数执行的代码...(省略)...
---- testB end----
---- testA end----
所谓的作用域是指有效的作用空间,在程序中是指某个变量或者数据作用的地方大小
结构:
def 函数名(参数):
变量名称 # 这个变量就是局部变量
结构:
变量名称 # 这个变量就是全局变量
def 函数(参数):
代码
举例:
# 定义全局变量
a = 100
def test1():
a = 300 # 定义局部变量
print('-----test1----修改前---a=%d' % a)
a = 200
print('-----test1----修改后---a=%d' % a)
def test2():
print('-----test2---a=%d' % a)
# 调用函数
test1()
test2()
运行结果:
-----test1----修改前---a=300
-----test1----修改后---a=200
-----test2---a=100
当函数内出现局部变量和全局变量相同名字时,函数内部中的 变量名 = 数据
此时理解为定义了一个局部变量,而不是修改全局变量的值
结构:
变量名称 # 定义全局变量
def 函数名(参数):
global 变量名称 # 声明使用的是全局变量
代码
举例:
# 全局变量和局部变量名称相同例子
# 定义全局变量
a = 100
def test1():
global a # 声明全局变量
print('-----test1----修改前---a=%d' % a)
a = 200
print('-----test1----修改后---a=%d' % a)
def test2():
print('-----test2---a=%d' % a)
# 调用函数
test1()
test2()
运行结果:
-----test1----修改前---a=100
-----test1----修改后---a=200
-----test2---a=200
变量名 = 数据
也理解为对全局变量进行修改,而不是定义局部变量# 可以使用一次global对多个全局变量进行声明
global a, b
# 还可以用多次global声明都是可以的
# global a
# global b
函数之间共享数据的方法如下:
举例:
g_num = 0
def test1():
global g_num
# 将处理结果存储到全局变量g_num中
g_num = 100
def test2():
# 通过获取全局变量g_num的值,从而获得test1函数处理之后的结果
print(g_num)
# 1.先调用test1得到数据保存到全局变量中
test1()
# 2.在调用test2,处理test1函数执行之后的这个值
test2()
运行结果:
100
函数之间共享变量可以使用全局变量作为媒介来存储和转发数据从而达到共享数据的结果
举例:
def test1():
# 通过return将一个数据结果返回
return 50
def test2(num):
# 通过形参的方式保存传递过来的数据,就可以处理了
print(num)
# 1. 先调用test1得到数据并且存到变量result中
result = test1()
# 2. 调用test2时,将result的值传递到test2中,从而让这个函数对其进行处理
test2(result)
运行结果:
50
举例:
def test1():
# 通过return将一个数据结果返回
return 20
def test2():
# 1. 先调用test1并且把结果返回来
result = test1()
# 2. 对result进行处理
print(result)
# 调用test2时,完成所有的处理
test2()
运行结果:
20
所谓的拆包就是将python特殊结构的数据直接分开存储的过程
举例:
# 直接对函数的返回值进行拆包
def get_my_info():
high = 178
weight = 100
age = 18
return high, weight, age
my_high, my_weight, my_age = get_my_info()
print(my_high)
print(my_weight)
print(my_age)
运行结果:
178
100
18
注意:
举例:
In [17]: a, b = (11, 22)
In [18]: a
Out[18]: 11
In [19]: b
Out[19]: 22
In [20]: a, b = [11, 22]
In [21]: a
Out[21]: 11
In [22]: b
Out[22]: 22
In [23]: a, b = {
"m":11, "n":22} # 取出来的是key,而不是键值对
In [24]: a
Out[24]: 'm'
In [25]: b
Out[25]: 'n'
交换变量的方法有很多
方法一:借用第三方帮助
举例:
a = 4
b = 5
c = 0 # 第三方
# 交换开始
c = a
a = b
b = c
print(a)
print(b)
方法二:计算法
举例:
a = 4
b = 5
# 开始计算
a = a+b # a=9, b=5
b = a-b # a=9, b=4
a = a-b # a=5, b=4
print(a)
print(b)
方法三:拆包法
举例:
a, b = 4, 5
a, b = b, a
print(a)
print(b)
生活中我们用洗衣机洗衣服不比考虑洗衣机的构造和制造我们只需要直接把衣服丢进去即可,这种让其他专业的事物去做的思想就是面向对象,每一步我们都不需要亲力亲为,只需要关注结果就行。在编程中面向对象编程思想将数据与函数绑定到一起,分类进行封装,每个程序员只要负责分配给自己的分类,这样能够更快速的开发程序,减少了重复代码。
面向过程:根据业务逻辑从上到下写代码,每一步都是自己做。
面向对象:将数据与函数绑定到一起,分类进行封装,每个程序员只要负责分配给自己的分类,这样能够更快速的开发程序,减少了重复代码,每一步都照专业的人做
面向对象(object-oriented ;简称: OO) 至今还没有统一的概念 我这里把它定义为: 按人们 认识客观世界的系统思维方式,采用基于对象(实体)的概念建立模型,模拟客观世界分析、设 计、实现软件的办法。
面向对象编程(Object Oriented Programming-OOP) 是一种解决软件复用的设计和编程方法。 这种方法把软件系统中相近相似的操作逻辑和操作 应用数据、状态,以类的型式描述出来,以对象实例的形式在软件系统中复用,以达到提高软件开发效率的作用。
面向对象编程的2个非常重要的概念:类和对象
对象是面向对象编程的核心,在使用对象的过程中,为了将具有共同特征和行为的一组对象抽象定义,提出了另外一个新的概念——类
类就相当于制造飞机时的图纸,用它来进行创建的飞机就相当于对象
概念:
概念:
类和对象的关系好比就是做饼的模子和饼之间的关系,通过模子来制造饼。类就是创建对象的模板
类(Class) 由3个部分构成
举例:
# 猫类
类名:猫(cat)
属性:品种 、毛色、性别、名字、 腿儿的数量
方法(行为/功能):叫 、跑、吃、摇尾巴
如何把日常生活中的事物抽象成程序中的类?
拥有相同(或者类似)属性和行为的对象都可以抽像出一个类
方法:一般名词都是类(名词提炼法)
Eg:
小明正在使用电脑编程
小明 -->可以抽像成人类
电脑 -->可以抽像成电脑类
格式:
class 类名称:
方法列表
举例:
# class Hero: # 经典类(旧式类)定义形式
# 定义一个英雄类
class Hero(object):
def info(self):
print("英雄莫问出处")
说明:
详细格式:
class 类名(object):
def 方法1(self,参数列表) # 必须是self
pass
def 方法2(self,参数列表)
pass
python中,可以根据已经定义的类去创建出一个或多个对象。
格式:
对象名 = 类名()
举例:
class Hero(object):
def info(self):
"""info 是一个实例方法,类对象可以调用实例方法,实例方法的第一个参数一定是self"""
print(self)
"""当对象调用实例方法时,Python会自动将对象本身的引用做为参数,传递到实例方法的第一个参数self里"""
print("self各不同,对象是出处")
# Hero这个类 实例化了一个对象
super_man = Hero()
# 对象调用实例方法info(),执行info()里的代码
# . 表示选择属性或者方法
super_man.info()
print(super_man) # 打印对象,则默认打印对象在内存的地址,结果等同于info里的print(self)
print(id(super_man)) # id(super_man)则是内存地址的十进制形式表示
class Hero(object):
"""定义了一个英雄类,可以移动和攻击"""
def move(self):
"""实例方法"""
print("正在前往事发地点...")
def attack(self):
"""实例方法"""
print("发出了一招强力的普通攻击...")
# 实例化了一个英雄对象 泰达米尔
taidamier = Hero()
# 给对象添加属性,以及对应的属性值
taidamier.name = "泰达米尔" # 姓名
taidamier.hp = 2600 # 生命值
taidamier.atk = 450 # 攻击力
taidamier.armor = 200 # 护甲值
# 通过.成员选择运算符,获取对象的属性值
print("英雄 %s 的生命值 :%d" % (taidamier.name, taidamier.hp))
print("英雄 %s 的攻击力 :%d" % (taidamier.name, taidamier.atk))
print("英雄 %s 的护甲值 :%d" % (taidamier.name, taidamier.armor))
# 通过.成员选择运算符,获取对象的实例方法
taidamier.move()
taidamier.attack()
class Hero(object):
"""定义了一个英雄类,可以移动和攻击"""
def move(self):
"""实例方法"""
print("正在前往事发地点...")
def attack(self):
"""实例方法"""
print("发出了一招强力的普通攻击...")
def info(self):
"""在类的实例方法中,通过self获取该对象的属性"""
print("英雄 %s 的生命值 :%d" % (self.name, self.hp))
print("英雄 %s 的攻击力 :%d" % (self.name, self.atk))
print("英雄 %s 的护甲值 :%d" % (self.name, self.armor))
# 实例化了一个英雄对象 泰达米尔
taidamier = Hero()
# 给对象添加属性,以及对应的属性值
taidamier.name = "泰达米尔" # 姓名
taidamier.hp = 2600 # 生命值
taidamier.atk = 450 # 攻击力
taidamier.armor = 200 # 护甲值
# 通过.成员选择运算符,获取对象的实例方法
taidamier.info() # 只需要调用实例方法info(),即可获取英雄的属性
taidamier.move()
taidamier.attack()
所谓的魔法方法是在python类里提供的,两个下划线开始,两个下划线结束的方法。
init()就是一个魔法方法,通常用来做属性初始化 或 赋值 操作。 如果类面没有写__init__方法,Python会自动创建,但是不执行任何操作,如果为了能够在完成自己想要的功能,可以自己定义__init__方法, 所以一个类里无论自己是否编写__init__方法一定有__init__方法。
结构:
class 类名称(object):
def __init__(self):
属性/赋值
举例:
class Hero(object):
"""定义了一个英雄类,可以移动和攻击"""
def __init__(self):
""" 方法,用来做变量初始化 或 赋值 操作,在类实例化对象的时候,会被自动调用"""
self.name = "泰达米尔" # 姓名
self.hp = 2600 # 生命值
self.atk = 450 # 攻击力
self.armor = 200 # 护甲值
def move(self):
"""实例方法"""
print("正在前往事发地点...")
def attack(self):
"""实例方法"""
print("发出了一招强力的普通攻击...")
# 实例化了一个英雄对象,并自动调用__init__()方法
taidamier = Hero()
# 通过.成员选择运算符,获取对象的实例方法
taidamier.info() # 只需要调用实例方法info(),即可获取英雄的属性
taidamier.move()
taidamier.attack()
说明:
结构:
class 类名称(object):
def __init__(self):
属性/赋值
举例:
class Hero(object):
"""定义了一个英雄类,可以移动和攻击"""
def __init__(self, name, skill, hp, atk, armor):
""" __init__() 方法,用来做变量初始化 或 赋值 操作"""
# 英雄名
self.name = name
# 技能
self.skill = skill
# 生命值:
self.hp = hp
# 攻击力
self.atk = atk
# 护甲值
self.armor = armor
def move(self):
"""实例方法"""
print("%s 正在前往事发地点..." % self.name)
def attack(self):
"""实例方法"""
print("发出了一招强力的%s..." % self.skill)
def info(self):
print("英雄 %s 的生命值 :%d" % (self.name, self.hp))
print("英雄 %s 的攻击力 :%d" % (self.name, self.atk))
print("英雄 %s 的护甲值 :%d" % (self.name, self.armor))
# 实例化英雄对象时,参数会传递到对象的__init__()方法里
taidamier = Hero("泰达米尔", "旋风斩", 2600, 450, 200)
gailun = Hero("盖伦", "大宝剑", 4200, 260, 400)
# print(gailun)
# print(taidamier)
# 不同对象的属性值的单独保存
print(id(taidamier.name))
print(id(gailun.name))
# 同一个类的不同对象,实例方法共享
print(id(taidamier.move()))
print(id(gailun.move()))
说明:
1.当使用类名()创建对象时,会自动执行以下操作
改造初始化方法
在开发中如果希望在创建对象的同时就设置对象的属性就要对__init__进行改造
1、把希望设置的属性值,定义成init方法的参数
2、在方法内部使用self.属性 = 形参接受外部传递的参数
3、在创建对象时,使用类名(属性1,属性2,。。。)调用
注意:
这个方法是一个魔法方法 (Magic Method) ,用来显示信息 该方法需要 return 一个数据,并且只有self一个参数,当在类的外部 print(对象) 则打印这个数据
如果在开发中,希望输出对象变量时,能够打印自定义内容,就可以使用__strl__这个内置方法
注意:str方法必须有一个返回值
结构:
class 类名称(object):
def __init__(self,参数列表):
属性/赋值
def __str__(self):
return 信息
举例:
class Hero(object):
"""定义了一个英雄类,可以移动和攻击"""
def __init__(self, name, skill, hp, atk, armor):
""" __init__() 方法,用来做变量初始化 或 赋值 操作"""
# 英雄名
self.name = name # 实例变量
# 技能
self.skill = skill
# 生命值:
self.hp = hp # 实例变量
# 攻击力
self.atk = atk
# 护甲值
self.armor = armor
def move(self):
"""实例方法"""
print("%s 正在前往事发地点..." % self.name)
def attack(self):
"""实例方法"""
print("发出了一招强力的%s..." % self.skill)
# def info(self):
# print("英雄 %s 的生命值 :%d" % (self.name, self.hp))
# print("英雄 %s 的攻击力 :%d" % (self.name, self.atk))
# print("英雄 %s 的护甲值 :%d" % (self.name, self.armor))
def __str__(self):
"""
这个方法是一个魔法方法 (Magic Method) ,用来显示信息
该方法需要 return 一个数据,并且只有self一个参数,当在类的外部 print(对象) 则打印这个数据
"""
return "英雄 <%s> 数据: 生命值 %d, 攻击力 %d, 护甲值 %d" % (self.name, self.hp, self.atk, self.armor)
taidamier = Hero("泰达米尔", "旋风斩", 2600, 450, 200)
gailun = Hero("盖伦", "大宝剑", 4200, 260, 400)
# 如果没有__str__ 则默认打印 对象在内存的地址。
# 当类的实例化对象 拥有 __str__ 方法后,那么打印对象则打印 __str__ 的返回值。
print(taidamier)
print(gailun)
# 查看类的文档说明,也就是类的注释
print(Hero.__doc__)
运行结果:
英雄 <泰达米尔> 数据: 生命值 2600, 攻击力 450, 护甲值 200
英雄 <盖伦> 数据: 生命值 4200, 攻击力 260, 护甲值 400
定义了一个英雄类,可以移动和攻击
结构:
class 类名称(object):
def __init__(self,参数列表):
属性/赋值
def __str__(self):
return 信息
def __del__(self,参数列表):
代码
举例:
class Hero(object):
# 初始化方法
# 创建完对象后会自动被调用
def __init__(self, name):
print('__init__方法被调用')
self.name = name
# 当对象被删除时,会自动被调用
def __del__(self):
print("__del__方法被调用")
print("%s 被 GM 干掉了..." % self.name)
# 创建对象
taidamier = Hero("泰达米尔")
# 删除对象
print("%d 被删除1次" % id(taidamier))
del(taidamier)
print("--" * 10)
gailun = Hero("盖伦")
gailun1 = gailun
gailun2 = gailun
print("%d 被删除1次" % id(gailun))
del(gailun)
print("%d 被删除1次" % id(gailun1))
del(gailun1)
print("%d 被删除1次" % id(gailun2))
del(gailun2)
应用场景:
1、当一个对象被调用类名()创建,生命周期开始
2、一个对象的__del__方法一旦被调用,生命周期结束
3、对面向对象生命周期内,可以访问对象属性或者让对象调用方法
在生活中继承的含义一般是子女继承父辈的财产,而在程序中是指,类继承另外一个类的属性和方法。
继承的概念:子类拥有父类的所有属性和方法
举例:
# 父类
class A(object):
def __init__(self):
self.num = 10
def print_num(self):
print(self.num + 10)
# 子类
class B(A):
pass
b = B()
print(b.num)
b.print_num()
运行结果:
10
20
结构
class 类名称(父类名):
方法/属性
举例:
# 老猫将自己的一身本领传给小猫
# 定一个父类
class Cat(object):
def __init__(self):
self.kongfu = "厉害的捉鱼本领"
def make_fish(self):
print("利用%s抓鱼" % self.kongfu)
# MinCat,继承了Cat,Cat是父类。
class MinCat(Cat):
pass
xiaohua = MinCat()
print(xiaohua.kongfu)
xiaohua.make_fish()
运行结果:
厉害的捉鱼本领
利用厉害的捉鱼本领抓鱼
说明:
总结:
结构:
class 类名称(父类名1,父类名2):
方法/属性
举例:
# 老猫将自己的一身本领传给小猫,同时狗狗也将自己看家的本事传给了小猫
# 定一个父类
class Cat(object):
def __init__(self):
self.kongfu = "厉害的捉鱼本领"
def make_fish(self):
print("利用%s抓鱼" % self.kongfu)
# 定义第二个父类
class Dog(object):
def __init__(self):
self.kongfu = "厉害的看家本领"
def kanmen(self):
print("利用%s看家" % self.kongfu)
# MinCat,继承了Cat、Dog,Cat、Dog是父类。
class MinCat(Cat,Dog):
pass
xiaohua = MinCat()
print(xiaohua.kongfu)
xiaohua.make_fish()
xiaohua.kanmen()
运行结果:
厉害的捉鱼本领
利用厉害的捉鱼本领抓鱼
利用厉害的捉鱼本领看家
说明:
子类的魔法属性__mro__决定了属性和方法的查找顺序
列子:
# 老猫将自己的一身本领传给小猫,同时狗狗也将自己看家的本事传给了小猫
# 定一个父类
class Cat(object):
def __init__(self):
self.kongfu = "厉害的捉鱼本领"
def make_fish(self):
print("利用%s抓鱼" % self.kongfu)
# 定义第二个父类
class Dog(object):
def __init__(self):
self.kongfu = "厉害的看家本领"
def kanmen(self):
print("利用%s看家" % self.kongfu)
# MinCat,继承了Cat、Dog,Cat、Dog是父类。
class MinCat(Cat, Dog):
pass
xiaohua = MinCat()
print(MinCat.__mro__)
运行结果:
(<class '__main__.MinCat'>, <class '__main__.Cat'>, <class '__main__.Dog'>, <class 'object'>)
注意:如果多个父类中有同名的 属性和方法,则默认使用第一个父类的属性和方法(根据类的魔法属性mro的顺序来查找)