基础知识
提醒:仔细读代码,通过代码理解知识点的使用方法,相关概念需要自己去查
注释
#这是一个单行注释
'''
这是一个多行注释
这是一个多行注释
这是一个多行注释
'''
"""
这是一个多行注释
这是一个多行注释
这是一个多行注释
"""
注意:多行注释不能与代码块在同一行,负责会被认为是一个字符串或者报错
n = 1 """111"""
^
#报错信息:SyntaxError: invalid syntax
基本语法
缩进:在python中使用缩进来表示代码逻辑,也就是说,python每段代码块缩进的空白数量可以是任意,但要确保同段代码块语句必须包含相同的缩进空白数量。
a = input("请输入一个数")
b = input("请输入一个数")
if a>b:
print(a)
else:
print(b)
多行语句
如果一条语句过长需要多行输出,那么可以使用圆括号(),反斜杠“\”来实现分行
Str1 = ("一个语句过长,导致编译器的窗口宽度不能完全显示时,\
可以在语句外部加上一堆圆括号来实现,\
也可以使用反斜杠来实现分行书写功能")
print(Str1)
#运行结结果:一个语句过长,导致编译器的窗口宽度不能完全显示时,可以在语句外部加上一堆圆括号来实现,
也可以使用反斜杠来实现分行书写功能
变量和基本的数据类型
变量:内存中命名的存储位置,值可以动态变化
result = 30 #定义一个整型变量
name = "guanguan" #定义一个字符串变量
float_num = 3.14 #定义一个浮点型的变量
f1 = 4.5+3j #定义一个复数类型的变量
print(f1.real) #4.5实部、实数
print(f1.imag) #3虚数
#布尔类型是一种特殊的整型。True = 1,False = 0
a = [] #这是一个列表
a1 = {} #字典类型
a2 = () #这是一个元组类型
a3 = set() #这是一个集合类型
标识符命名规则:只能是字母、数字、下划线_,组合而成,但必须以字母或者下划线开头,一般
来说我们会使用驼峰命名规则,如:Writh_Name
关键字:python预先定义了一部分有特殊意义的标识符,
运算符
算术运算符,+、-、*、/(3/2=1.5)、//(3//2 = 1)、%(17/10 = 7)、**(2**3 =8)
赋值运算符: =
比较运算符:<、<=、>、>=、==、!=,is 、is not
逻辑运算符:and(与)、or(或) 、not(非)
位运算:&(1+1 = 1,1+0=0,0+0 = 0),|(1+1=1,1+0 = 1,0+0 =0),^(1+1 = 0,0+0 = 0,1+0 =1)
字符串定义
#单引号
a = 'hello word'
#双引号
b = "hello word"
#三引号
c = """hello
word
"""
print(a) #hello word
print(b) #hello word
printf(c)
#hello
#word
格式化字符串
#输入姓名年龄
a = "I am %s. I am %d years old."%('Lucy',20)
print(a)
#I am Lucy. I am 20 years old.
format() 方法
#位置参数
print("{} is {} years old.".format("Lucy",20))
#Lucy is 20 years old.
#键值对
print("{name} is {age} years old.".format(name = "Lucy",age = "20"))
#Lucy is 20 years old.
#参数是列表或者元组
st = ["Lucy",20]
school = ("yunnan","YNJD")
print("{1[0]} was born in {0[0]},she is {1[1]} years old.".format(school,st))
#Lucy was born in yunnan,she is 20 years old.
字符串的比较
从索引为0的地方开始比较,直到出现不同字符,根据ASCII值比较,该字符串第一个不同字符的
大小来判断谁大谁小。
a = 'acb'
b = 'abc'
#第一个不同的字符是c和b,c的ASCII值是99,b的ASCII值是97
print(a>b) #True
字符串输入输出
在python中 input()函数,从键盘上输入的数据,默认是字符串,因此当你要输入数字是要进行强制
类型转换。
#输入一个int类型数字
a = int(input("请输入一个数")) #这样就使得数据转换为int类型
字符串运算
+:连接字符串
*:重复输出字符串
[]:通过索引来访问字符串中的字符
[:]截取字符串
字符串内建方法(常用)
string.count(str,beg = 0,end =len(string))
#返回str在beg~end范围内出现的次数
string.find(str,beg=0,end =len(string))
# 返回str是否在beg~end范围内,是则返回开始的索引,否则返回-1
string.index(str,beg=0,end=len(string))
#返回str是否在beg~end范围内,是则返回开始的索引,否则报错
string.isnumeric() #string 是否只有数字字符,是True,否False
string .lower() #大写转小写
string.upper() #小写转大写
string.swapcase() #翻转大小写
string.rstrip() #删除末尾空格
string.split(str = " ",num=string.count(str))
#以str为分隔符切片string,如果num有特定值,则仅分割num个子字符
组合数据类型
python 的组合数据类型分为三种:
序列类型:字符串,列表,元组
映射类型:字典 ,用键值对表示数据
集合类型:集合,元素是无序的,元素是唯一的,不能有相同
列表
#创建列表
list1 = [] #可以存放任意数据类型
#删除列表元素 del list1[索引]
list1 = [11,20]
del list1[0]
print(list1) #[20]
#修改列表元素
list1 = [10,20]
list1[0] =20
print(list1) #[20,20]
#读取列表元素按索引读取
print(list1[0]) #20
#用for循环遍历
for item in list1:
print(item,end=',') #20,20
列表的方法
list.append(obj)/+ :末尾添加新对象
list.count(obj):统计obj在list中出现的次数
list.extend():将一个列表添加到原列表尾部
list.reverse():反向列表中元素
元组
#创建一个空元组
tup = ()
#注意:当元组只包含一个元素时,需要在元素后面加逗号,否则括号会被当做运算符使用
tup = (1,)
#删除元组,元组的元素值不能修改不能删除
tup = (1,2,3)
del tup
print(tup) #会报错,tup未定义
#修改元组不可以的,但是当元组中出现列表是,我们可以对列表元素进行修改
tup = (1,3,4,5,[1,2,3,4])
tup[4][1] = 5
print(tup) # (1,3,4,5,[1,5,3,4])
元组运算符
len() :计算元素个数
+ :连接
('*',)*4:复制4次 ('*','*','*','*',)
a in():a是否存在()
for x in (): 迭代 x 访问的是元组的元素
元组与列表的相互转换
tup1 = (357,"abc")
list1 = list(tup)
list1.append(246)
tup1 = tuple(list1)
print(tup1) #(357,"abc",246)
字典
#创建字典,键值对的形式存储key - value
dict1 = {}
#查找与反向查找字典元素,根据key的值来查找
dict1 = {"id":19,"name":Marry}
print(dict1["id"]) #19
#遍历字典
for key in dict1.keys():
print(key,dict[key])
#id:19
#name:Marry
#修改字典元素
dict1["id"] = 20
print(dict1) #"id":20,"name":Marry
#添加字典元素
dict1["email"] = "py@qq.com"
print(dict1) #"id":20,"name":Marry,"email":"py@qq.com"
#检索
key in dict1 #key是否在dict1内
字典常用函数
dict.get(key,default) :返回相应的值,否则返回默认值
dict.pop(key,default):返回相应值,同时删除键值对,否则返回默认值
dict.clear():删除所有键值对
dict.update(dict2):将一个字典中的值更新到另一个字典中
集合
注意:集合中元素无重复,创建是要使用set()函数
删除集合的三种方法:
1、remove(key):删除key,如果key不在集合中会报错
2、discard(key),删除key,如果key不在集合中也不会报错
3、clear() :清空集合
添加集合元素:
1、add() :把传入的元素作为整体添加到集合中
2、update() :把传入元素拆分成一个一个字符添加到集合里
流程控制
三种结构:顺序结构,选择结构,循环结构
顺序结构:自上而下执行
选择结构
单选择结构:if语句
if a>10:
print("True")
print("good")
"""
如果a >10
输出True
good
如果a<10
good
"""
双选择结构:if...else...
a = 10
b = 30
if a>b:
print(a)
else:
print(b)
#输出 30
多选择结构:if...elif...else
a = 10
if a<60:
print("不及格")
elif a<90:
print("良好")
else:
print("优秀")
#输出 不及格
循环结构
while 语句 :特点是先判断,后执行。
语法格式:
while (判断条件):
执行语句
i = 0
while(i<3):
i = i+1
print(i)
"""
输出结果
1
2
3
"""
for语句
语法格式:
for 变量 in 序列:
执行语句序列
经常使用的遍历方式有:
1、有限次遍历:for i in range(n):#n为遍历次数
2、遍历文件:for line in myfile:#myfile为文件的引用
3、遍历字符串:forch in mystring: #mystring是字符串的引用
4、遍历列表:for item in mylist:#mylist 为列表的引用
pass语句:用于占位,使得结构的完整性
break语句:退出循环
continue语句:进行下一次循环
判断10以内的奇偶数
for i in range(0,10):
if i%2 == 0:
print(i,"是偶数")
else:
print(i,"是奇数")
#输出
"""
0 是偶数
1 是奇数
2 是偶数
3 是奇数
4 是偶数
5 是奇数
6 是偶数
7 是奇数
8 是偶数
9 是奇数
"""
输出九九乘法表
for j in range(1,10):
for i in range(1,j+1):
print(i,"*",j,"=",j*i,"",end="")
print()
#输出
"""
1 * 1 = 1
1 * 2 = 2 2 * 2 = 4
1 * 3 = 3 2 * 3 = 6 3 * 3 = 9
1 * 4 = 4 2 * 4 = 8 3 * 4 = 12 4 * 4 = 16
1 * 5 = 5 2 * 5 = 10 3 * 5 = 15 4 * 5 = 20 5 * 5 = 25
1 * 6 = 6 2 * 6 = 12 3 * 6 = 18 4 * 6 = 24 5 * 6 = 30 6 * 6 = 36
1 * 7 = 7 2 * 7 = 14 3 * 7 = 21 4 * 7 = 28 5 * 7 = 35 6 * 7 = 42 7 * 7 = 49
1 * 8 = 8 2 * 8 = 16 3 * 8 = 24 4 * 8 = 32 5 * 8 = 40 6 * 8 = 48 7 * 8 = 56 8 * 8 = 64
1 * 9 = 9 2 * 9 = 18 3 * 9 = 27 4 * 9 = 36 5 * 9 = 45 6 * 9 = 54 7 * 9 = 63 8 * 9 = 72 9 * 9 = 81
"""
函数
函数定义使用def关键字来定义
#函数定义
def 函数名(参数1,参数2):#参数1和参数2是形式参数
"""
执行语句块
"""
return 返回值
#函数调用
a = 函数名(实参1,实参2)#实参1和实参2是实参 //使用一个a来接收函数的返回值
递归函数
如计算n的阶乘
def f(n):
if n == 1:
return 1;
else:
return f(n-1)*n
n = int(input("请输入一个正数:"))
print(n,"阶乘结果为",f(n))
"""
请输入一个正数:3
3 阶乘结果为 6
"""
匿名函数
关键字lambda用于定义一种特殊函数--匿名函数
语法格式:
函数名 = lambda [参数列表 ]:表达式
sum = lambda arg1,arg2:arg1+arg2
print(sum(20,50)) #arg1 = 20,arg2 = 50
#输出 70
变量的作用域
a = 200 #a = 200是全局变量
def f(a):
a = 10 #在函数内部定义属于局部变量
print(a) #输出10
return a
f(a)
print(a) #输出200
内置函数
abs():求绝对值
print(abs(-5.21))
#5.21
pow():求幂函数
pow(x,y) #求x的y次方
print(pow(3,4)) #81
max():求最大值
print(max(3,4)) #4
min():求最小值
print(min(3,4)) #3
sum():求和函数
print(sum(1,1)) #2
还有很多我就不一一列举了,自己可以上网上查一下没有涉及到的函数
期中我们就考到这里,快期末再发后面的内容。
眨眼就到期末了
正则表达式
定义
正则表达式:又名为“规则表达式”,实际上是一个“文本模式”,通过一个字符串序列来定义一种搜索模式,其用途主要用于字符串模式匹配或字符串匹配(简单来说就是查找和替换操作)。
学习正则表达式的时候给大家推荐一个网站http://regex101.com,这个网站能够测试我们的正则表达式是否正确,当然该网站的一些规则也是需要注意的,具体的就自己去试验一下啦。记得使用网站时要选择对应的语言。下面是我的一个测试案例,“\d”匹配的是数字,因此匹配上的字符都显示出,并且在右边也会给出提示。
python中的字符
1、非打印字符
例如:
\n:匹配一个换行符
\r:匹配一个回车符
\s:匹配任意空白字符,包括空格,制表符,换页符等等
2、特殊字符
例如:
*:匹配前面的子表达式0次或多次
.:匹配出换行符以外的任何单字符
|:指明两项之间的一个选择
?:匹配前面的子表达式零次或一次,或指明一个非贪婪限定符。要匹配?字符,请使用\?
3、数量限定符(比较重要)
限定符:用来指定正则表达式的一个给定组件必须出现多少次才能满足匹配。
*:匹配前面的子表达式0次或多次
例如:
?:匹配前面的子表达式零次或一次
例如:
+:匹配前面的子表达式一次或多次
{n}:n是一个非负整数。用来匹配前面的字符串n次
{n,}:n是一个非负整数,至少匹配n次
{n,m}:n,m均为非负整数,n<=m,最少匹配n次最多匹配m次
一共有6种限定符
4、定位符
定位符能够将正则表达式固定到行首或行尾。
^和$分别指定字符串的开始和结尾
\b:描述单词前面的前或后边界
\B:表示非单词边界匹配
5、正则表达式特殊序列
\d:匹配一个数字字符
\w:匹配一个单词字符,包括字母、数字、下划线
还有一些字符在这里就不一一列举了,有需要的可以上网查询
如何在python中使用正则表达式?
在Python中使用正则表达式首先需要导入re模块,该模块使得python语言拥有全部的正则表达式功能,re模块提供了一些函数,如compile()函数,match()函数,search()函数等等
compile()函数
用来对正则表达式进行编译和处理正则表达式对象
re.compile(pattern,flags=0)
#flags是可选的编译标志,返回一个pattern对象
例如:
import re #导入re模块
# 定义要匹配的正则表达式模式
pattern = r'\d+' # 匹配一个或多个数字
# 使用 compile 函数编译正则表达式模式
# 参数 're.IGNORECASE' 表示忽略大小写
compiled_pattern = re.compile(pattern, re.IGNORECASE)
# 待匹配的字符串
text = "Here are some numbers: 123, 456 and 789."
# 使用编译后的正则表达式进行搜索
matches = compiled_pattern.findall(text)
# 输出匹配结果
print("Matches found:", matches)
match()函数
用于匹配对象,格式如下
re.match(pattern,string,flags = 0)
例如:
import re
# 定义要匹配的正则表达式模式
# 例如,我们想要匹配以特定前缀开头的字符串
pattern = r'^Hello'
# 待匹配的字符串
test_string = "Hello World"
# 使用 re.match 函数进行匹配
match = re.match(pattern, test_string)
# 检查是否有匹配
if match:
print("匹配成功,匹配位置从:", match.start())
print("匹配的字符串:", match.group())
else:
print("没有匹配")
search()函数
搜索字符串。格式如下
re.search(pattern,string,flags = 0)
例如:
import re
# 定义要搜索的正则表达式模式
# 例如,我们想要搜索包含数字的字符串
pattern = r'\d+'
# 待搜索的字符串
test_string = "Here are two numbers: 123 and 456."
# 使用 re.search 函数进行搜索
match = re.search(pattern, test_string)
# 检查是否有匹配
if match:
print("匹配成功,匹配位置从:", match.start())
print("匹配的字符串:", match.group())
else:
print("没有匹配")
其他相关的知识点可以去该网站查https://www.runoob.com/python/python-reg-expressions.html
面向对象编程
对象的概念:现实世界只客观存在的事物称对象,任何对像都有具有各自的特征(也就是属性),和行为(也就是方法)。
类和对象
类是通过关键字class创建的
#定义一个Person类
class Person:
name = "张三" #成员变量,也称为属性
def printname(self): #成员函数 也叫成员方法
print(self.name)
p = Person() #创建一个Person对象
p.printname() #调用成员函数
属性和方法
类属性
#定义一个Person类
class Person:
name = "张三" #公有属性
__age = "19" #私有属性 定义私有属性时需要使用两个下划线 __
p = Person() #创建一个Person对象
Name = p.name #能够在类外访问公有成员
print(Name) #张三
#age = p.__age #错误,不能在类外访问私有成员
实例属性
不需要再类中显式定义,而在__init__构造函数中定义,定义时以self.作为前缀
例如:
class Person:
def __init__(self, name, age):
# 实例属性,每个实例有自己的值
self.name = name # 'self' 是对当前对象实例的引用
self.age = age
# 创建 Person 类的两个实例
person1 = Person("Alice", 30)
person2 = Person("Bob", 25)
# 访问实例属性
print(person1.name) # 输出: Alice
print(person1.age) # 输出: 30
print(person2.name) # 输出: Bob
print(person2.age) # 输出: 25
# 也可以修改实例属性的值
person1.age = 31
print(person1.age) # 输出: 31
类的方法
方法是与类相关的函数。并且方法与函数不同,函数是封装操作的小程序方法是定义在类内部的函数,并且定义方法与普通函数有所不同。
类的方法主要有三种类型:实例方法、类方法以及静态方法
实例方法:
class Person:
def getPlace(self,name): #实例方法
self.name = name
return self.name
p = Person()
print(p.getPlace("张三")) #通过实例对象来调用
实例方法声明格式:
def 方法名(self,[形参列表]):
函数体
实例方法通过实例对象调用:
对象.方法名([实参列表])
类方法
类方法需要用修饰器“@classmethod”来标识其为类方法,对于类方法,第一个参数必须是类对象,一般以“cls”作为这一个参数,类方法可通过实例对象和类对象去访问。
类方法的声明格式:
@classmethod
def 类方法名(cls,[形参列表]):
函数体
类方法调用格式:
类名.类方法([实参列表])
class Person:
place = "张三"
@classmethod
def getplace(cls):
return cls.place
p = Person()
print(p.getplace()) #通过实例对象调用
print(Person.getplace()) #通过类对象调用
此外,类方法可以对类属性进行修改
class Person:
place = "张三"
@classmethod
def getplace(cls):
return cls.place
@classmethod
def setplace(cls,placel):
cls.place = placel
p = Person()
p.setplace("李四") #修改类属性
print(p.getplace()) #输出李四
静态方法
静态方法需要通过修饰器“@staticmethod”来修饰,静态方法不需要多定义参数,通过类名访问,不支持修改,不需要实例化。
class Person:
place = '张三'
@staticmethod #静态方法
def getplace():
return Person.place
print(Person.getplace()) #使用类名访问
构造方法和析构方法
构造方法
特征 :__init__(self,)在生成对象时调用,可以用来进行一些属性初始化操作,不需要显式去调用,系统会默认执行,构造方法支持重载,如果用户自己没有重新定义构造方法,系统会自动执行默认的构造方法。
class Person:
def __init__(self,name):
self.personname = name
def sayHai(self):
print('我是:',self.personname)
p = Person('张三')
p.sayHai()
析构方法
析构方法__del__(self)在释放对象时调用,支持重载,可以在其中进行一些释放资源的操作,不需要显式调用。下面举一个例子来区分方法的执行顺序:
class test:
def __init__(self):
print("构造方法")
def __del__(self):
print("析构方法")
def myf(self):
print("调用自定义方法")
obj = test()
obj.myf()
del obj
属性和方法的访问控制
在Python中,属性和方法的访问控制是通过名称前缀来实现的
class Person:
name = "张三" #公有属性
age = "18"
__name = "李四" #私有属性
__age = "18"
def getname(self):
return self.__name
def getage(self):
return self.__age
p = Person()
print(p.name,p.age)
# p.__age 私有属性不能直接访问,会报错
# p.__name
print(p.getname(),p.getage())
继承*
定义:继承用于指定一个类将从其父类获取其大部分或全部功能。
格式:
class 子类名(父类名,(可以多个父类))
类体
例如:创建父类A,包含两个数据成员s1和n1,由父类A派生出子类B,包含两个数据成员s2和n2,再由子类B派生出孙类C,包含两个类成员s3和n3.
class A():
def __init__(self,s1,n1):
self.s1 = s1
self.n1 = n1
print("父类",self.s1,self.n1)
class B(A):
def __init__(self,s1,n1,s2,n2):
super(B,self).__init__(s1,n1)
self.s2 = s2
self.n2 = n2
print("子类:",self.s2,self.n2)
class C(B):
def __init__(self,s1,n1,s2,n2,s3,n3):
super(C,self).__init__(s1,n1,s2,n2)
self.s3 = s3
self.n3 = n3
print("孙子类:",self.s3,self.n3)
if __name__ == "__main__":
a = A("s1","n1")
b = B("s1","n1","s2","n2")
c = C("s1","n1","s2","n2","s3","n3")
多态*
多态即多种形态,在运行时确定其状态,在编译阶段无法确定其类型,这就是多态。
多态性:向不同对象发送同一条消息,不同对象在接收时会产生不同的行为(即方法)
例如:我们所熟知的len函数不紧可以通过计算字符串的长度,还可以计算列表、元组等对象中的数据个数
例子:
class Animal:
def speak(self):
raise NotImplementedError("子类必须实现这个方法")
class Dog(Animal):
def speak(self):
return "Woof!"
class Cat(Animal):
def speak(self):
return "Meow!"
# 运行时多态:使用相同的接口调用不同对象的行为
def animal_sound(animal):
print(animal.speak())
dog = Dog()
cat = Cat()
animal_sound(dog) # 输出: Woof!
animal_sound(cat) # 输出: Meow!
在这个例子中:
-`Animal` 类是一个抽象基类,它定义了一个抽象方法 `speak`,这个方法在 `Dog` 和 `Cat` 子类中被重写。
`Dog` 和 `Cat` 类通过重写 `speak` 方法展示了运行时多态。尽管 `animal_sound` 函数使用相同的接口调用 `speak` 方法,但实际执行的是根据不同对象类型(`Dog` 或 `Cat`)动态绑定的方法。
当我们创建 `Dog` 和 `Cat` 的实例并调用 `animal_sound` 函数时,Python解释器在运行时确定调用哪个 `speak` 方法,这就是运行时多态的体现。
封装*
封装数据主要原因是保护隐私。
封装分为两个层面:
第一个层面的封装:创建类和对象会分别创建两者的名称空间,只能用“类名.”或者“实例名.”的方式去访问里面的属性和方法。
第二个层面的封装:类中把某些属性和方法隐藏起来(或者说定义成私有的),只在类的内部使用,外部无法访问,或者留下少量接口供外部访问。
封装需要仔细读这个代码,理清它的逻辑,观察子类是如何访问父类的私有成员的
class Car:
def __init__(self, model, year):
self.model = model # 公有属性
self.__year = year # 私有属性
def start(self):
# 公有方法
print(f"The {self.model} starts.")
def _repair(self):
# 保护方法,按照惯例不由类外部调用
print(f"The {self.model} is being repaired.")
# 私有方法,通常用于内部逻辑
def __private_method(self):
print("This is a private method.")
# 创建Car的实例
my_car = Car("Toyota", 2021)
# 访问公有属性和方法
print(my_car.model) # 输出: Toyota
my_car.start() # 输出: The Toyota starts.
# 尝试访问私有属性将引发错误
# print(my_car.__year) # 引发 AttributeError
# 私有方法在类外部不可见
# my_car.__private_method() # 引发 AttributeError
未完待续....
家人们有什么建议欢迎评论区留言或私信。