详解Python面向对象程序设计
Python面向对象程序设计
- 1,初识类和对象
- 2,类的定义和使用
- 3,构造方法
- 4,常用的类内置方法
- 4.1,字符串方法:`__str__ `
- 4.2,是否小于:`__lt__`
- 4.3,是否小于等于:`__le__`
- 4.4,是否相等:`__eq__`
- 5,面向对象的特性:封装
- 6,面向对象的特性:继承
- 6.1,继承的基础语法
- 6.2,复写父类成员
- 6.3,调用父类成员
- 7,Python类型注解
- 7.1,变量的类型注解
- 7.2,方法的类型注解
- 7.3,Union联合类型注解
- 8,面向对象的特性:多态
1,初识类和对象
设想这样一种场景:学校里每个学生都有各自的姓名、性别、班级、籍贯、年龄等个人信息。如果把每个人的信息写在一张纸上,组织起来就会非常混乱,因此在生活中常使用表格来记录学生的信息。
程序中,为了追求一种更简洁高效的数据表示形式,我们可以通过设计类、创建对象、给对象的属性赋值
的方法来组织数据。使用程序中的类可以完美的描述现实世界的事物。
- 设计一个类:类比整个学生群体
- 创建一个对象:类比某一位学生
- 对象属性赋值:类比填入某一位学生的信息
设计类,基于类创建对象,由对象做具体的工作,此即为面向对象编程
2,类的定义和使用
定义类和创建类对象的语法如下:
# 定义类的语法
class 类名称:类的属性# 类中定义成员方法def 方法名(self,形参1,......,形参N)方法体# 创建类对象的语法
对象 = 类名称()
- class是关键字,表示要定义类
- 类的
属性
,即定义在类中的变量(成员变量
) - 类的
行为
,即定义在类中的方法(成员方法
) - 类中可以定义属性来记录数据,定义函数来记录行为
self表示类对象自身
,当我们使用类对象调用方法时,self会自动被python传入self是成员方法定义的时候,必须填写的
在方法内部想要访问类的属性,必须使用self
- self关键字在方法的参数列表中,但传参的时候可以忽略它
案例演示:
# 设计一个类
class Student:# 各属性的初始值设置空值name = None # 记录学生姓名gender = None # 记录学生性别nationality = None # 记录学生国籍native_place = None # 记录学生籍贯age = None # 记录学生年龄# 类的行为def say_hello1(self):# 成员方法的参数中self是必须的# 在方法内部想要访问类的属性,必须使用selfprint(f"Hi,大家好,我是{self.name}")def say_hello2(self, msg):print(f"Hi,{msg}")# 创建一个对象
stu1 = Student()# 对象属性赋值
stu1.name = "小明"
stu1.gender = "男"
stu1.nationality = "中国"
stu1.native_place = "山东省"
stu1.age = 18# 获取对象中记录的信息
print(f"学生姓名是:{stu1.name},学生性别是:{stu1.gender},学生年龄是:{stu1.age}")# 调用类内部的方法
stu1.say_hello1()
stu1.say_hello2("很高兴认识大家")
运行结果如下:
3,构造方法
前面我们学习了对象属性的赋值(如下图),显然之前的赋值方式略显繁琐,需要写很多行。
实际有一种更高效的传参方式:
- 在创建对象的时候,像函数一样通过传参的形式对属性赋值,此即为构造方法。
Python类可以使用:
__init__()方法
,称之为构造方法,它可以实现:
- 在创建类对象的时候,会自动执行
- 在创建类对象的时候,将传入参数自动传递给
__init__()
方法使用 - 构造方法也是成员方法,不要忘记在参数列表中提供:
self
案例演示
"""
演示类的构造方法
"""class Student:# 此处成员变量的定义可省略,因为_init_方法会自动执行赋值,赋值的同时成员变量也被定义了name = Noneage = Nonetel = Nonedef __init__(self, name, age, tel):self.name = name # 表示内部的name属性等于外部传入的nameself.age = ageself.tel = telprint("Student类创建了一个类对象")# 使用构造方法创建类对象
stu = Student("小白",21,"13256666666")
print(stu.name)
print(stu.age)
运行结果如下:
4,常用的类内置方法
前面的__init__
构造方法,是Python类内置的方法之一。这些内置的方法,各自有各自特殊的功能,这些内置方法我们称之为:魔术方法。
方法 | 功能 |
---|---|
__init__ | 构造方法,可用于创建类对象的时候设置初始化行为 |
__str__ | 用于实现类对象转字符串的行为 |
__lt__ | 用于两个类对象进行小于或大于比较 |
__le__ | 用于两个类对象进行小于等于或大于等于比较 |
__eq__ | 用于两个类对象进行相等比较 |
4.1,字符串方法:__str__
__str__
是一个特殊方法(也称为魔术方法或双下方法),它定义了当对象需要被转换成字符串表示时应该如何做。
未定义__str__方法时,直接将对象打印输出或者将对象转为字符串输出,会输出对象的地址,代码示例如下:
class Student:def __init__(self, name, age, tel):self.name = name # 表示内部的name属性等于外部传入的nameself.age = ageself.tel = telprint("Student类创建了一个类对象")stu = Student("小白",21,"13256666666")# 直接将对象打印
print(stu)
# 将对象转为字符串打印输出
print(str(stu))
运行结果:
有时我们为了打印的时候显示对象中存储的数据内容,就可以通过定义
___str__
方法,控制类转换为字符串的行为。代码示例如下:
class Student:def __init__(self, name, age, tel):self.name = name # 表示内部的name属性等于外部传入的nameself.age = ageself.tel = tel# __str__魔术方法def __str__(self):return f"Student类对象,name:{self.name},age:{self.age},tel:{self.tel}"stu = Student("小白",21,"13256666666")# 打印输出
print(stu)
print(str(stu))
定义了魔术方法__str__后打印对象时就不再输出对象的内存地址 :
4.2,是否小于:__lt__
直接对两个对象进行比较大小是不可以的,但是在类中定义__lt__
方法,即可同时完成:小于符号和大于符号两种比较。
案例演示:
class Student:def __init__(self, name, age, tel):self.name = name # 表示内部的name属性等于外部传入的nameself.age = ageself.tel = tel# __str__魔术方法def __str__(self):return f"Student类对象,name:{self.name},age:{self.age},tel:{self.tel}"# __lt__魔术方法,other表示另外一个需要比较的类的对象def __lt__(self, other):return f"是否小于:{self.age < other.age}" # 返回一个布尔值stu1 = Student("小白",21,"13256666666")
stu2 = Student("小青",20,"13256666666")
stu3 = Student("小黄",20,"13256666666")# 是否小于
print(stu1 < stu2)
print(stu1 > stu2)
运行结果:
注意:如果不定义__str__
,直接两个对象比较会报错。
4.3,是否小于等于:__le__
在类中定义__le__
方法即可同时完成:小于等于符号和大于等于符号两种比较。
案例演示:
class Student:def __init__(self, name, age, tel):self.name = name # 表示内部的name属性等于外部传入的nameself.age = ageself.tel = tel# __str__魔术方法def __str__(self):return f"Student类对象,name:{self.name},age:{self.age},tel:{self.tel}"# __lt__魔术方法,other表示另外一个需要比较的类的对象def __lt__(self, other):return f"是否小于:{self.age < other.age}" # 返回一个布尔值# __le__魔术方法:是否小于等于def __le__(self, other):return f"是否小于等于:{self.age <= other.age}"# __eq__魔术方法:比较是否等于def __eq__(self, other):return f"是否等于:{self.age == other.age}"
stu1 = Student("小白",21,"13256666666")
stu2 = Student("小青",20,"13256666666")
stu3 = Student("小黄",20,"13256666666")# 是否小于
print(stu1 < stu2) # False
print(stu1 > stu2) # True# 是否小于等于
print(stu2 <= stu3)
print(stu2 >= stu3)
运行结果如下:
4.4,是否相等:__eq__
如果再类定义的时候没有定义__eq__
方法,使用“==”比较的话比较的是内存地址。
class Student:def __init__(self, name, age, tel):self.name = name # 表示内部的name属性等于外部传入的nameself.age = ageself.tel = tel# __str__魔术方法def __str__(self):return f"Student类对象,name:{self.name},age:{self.age},tel:{self.tel}"# __lt__魔术方法,other表示另外一个需要比较的类的对象def __lt__(self, other):return f"是否小于:{self.age < other.age}" # 返回一个布尔值# __le__魔术方法:是否小于等于def __le__(self, other):return f"是否小于等于:{self.age <= other.age}"stu1 = Student("小黄",20,"13256666666")
stu2 = Student("小黄",20,"13256666666")# 是否相等
print(stu1 == stu2)
运行结果如下:
如果类定义的时候定义了__eq__
方法,就可以按照__eq__
方法定义的比较规则实现比较对象存储的内容。
class Student:def __init__(self, name, age, tel):self.name = name # 表示内部的name属性等于外部传入的nameself.age = ageself.tel = tel# __str__魔术方法def __str__(self):return f"Student类对象,name:{self.name},age:{self.age},tel:{self.tel}"# __lt__魔术方法,other表示另外一个需要比较的类的对象def __lt__(self, other):return f"是否小于:{self.age < other.age}" # 返回一个布尔值# __le__魔术方法:是否小于等于def __le__(self, other):return f"是否小于等于:{self.age <= other.age}"# __eq__魔术方法:比较是否等于def __eq__(self, other):return f"年龄是否等于:{self.age == other.age}"stu1 = Student("小黄",20,"13256666666")
stu2 = Student("小黄",20,"13256666666")# 是否相等
print(stu1 == stu2)
运行结果如下:
5,面向对象的特性:封装
在日常生活中,当消费者使用手机、电视、洗衣机的时候,只需知道如何使用,而不必知晓其内部工作原理。此即为封装思想的体现:
在类中提供仅供内部使用的属性和方法,而不对外开放。
类中通过私有成员
的形式来实现属性和行为的封装:
- 私有成员变量:变量以
__
开头(两个下划线) - 私有成员方法:方法名以
__
开头(两个下划线) 类对象无法访问私有成员
私有成员可以被类内部的其他成员使用
代码示例一:
class Phone:__current_voltage = None # 当前手机运行电压def __keep_single_core(self): # 表示使cpu单核运行print("让CPU以单核模式运行")phone = Phone()
phone.__keep_single_core() # 报错
print(phone.__current_voltage) # 报错
运行结果如下:(类对象无法访问私有成员
)
代码示例二:私有成员可以被类内部的其他成员使用
class Phone:__current_voltage = 1 # 当前手机运行电压def __keep_single_core(self): # 表示使cpu单核运行print("让CPU以单核模式运行")def call_by_5g(self): # 电压大于1可以进行5g通话if self.__current_voltage >= 1:print("5g通话已开启")else:# 调用私有成员方法self.__keep_single_core()print("电压不足,无法使用5g童话,CPU已转为单核")phone = Phone()
phone.call_by_5g()
运行结果如下:
6,面向对象的特性:继承
为了促进了代码的复用和模块化,我们引入继承,通过继承一个基类,子类可以继承基类的所有特性,同时还可以添加新的特性或者覆盖基类中的方法。
6.1,继承的基础语法
继承语法:
class 类名(父类名):类内容体
Python中继承可以分为单继承和多继承
多继承的多个父类中,如果有同名的成员,默认继承顺序以从左到右为优先级
- 可以使用pass关键字做填充,补全语法
代码示例一 :单继承
演示一个手机类和新手机类之间的继承关系:
# 手机类
class Phone:seriesID = Noneproducer = "phone"def call_by_4g(self):print("4g通话")# 新手机类单继承父类(手机类)
class phone2024(Phone):# 面部识别ID(新属性)face_id = "10001"# 5g通话(新方法)def call_by_5g(self):print("5g童话")phone = phone2024()# 打印父类中定义过子类中没有定义的属性
print(f"phone.producer:{phone.producer}")
# 调用父类中定义过子类中没有定义的方法
phone.call_by_4g()
# 调用子类中新定义的方法
phone.call_by_5g()
运行结果如下 :
代码示例二:多继承
某些手机比如小米手机可以实现手机、NFC读卡器和红外遥控器…等功能。
因此我们可以定义一个小米手机类去继承手机类、NFC读卡器类和红外遥控器类。
# 手机类
class Phone:seriesID = Noneproducer = "phone"def call_by_4g(self):print("4g通话")# NFC读卡器类
class NFCReader:nfc_type = "第五代"producer = "NFCReader"def read_card(self):print("NFC读卡")def write_card(self):print("NFC写卡")# 红外遥控类
class RemoteControl:rc_type = "红外遥控"def control(self):print("红外遥控开启了")# 多继承
class XiaomiPhone(Phone, RemoteControl,NFCReader):# pass关键字用于不全语法。(不想添加语句,又要避免语法错误)passphone = XiaomiPhone()
# 4g通话
phone.call_by_4g()
# NFC写卡
phone.write_card()
# 红外遥控
phone.control()# 父类Phone和父类NFCReader里都有producter,但此处打印输出的是Phone中的producter
# 因为多继承的多个父类中,如果有同名的成员,默认继承顺序以从左到右为优先级
print(phone.producer)
运行结果如下:
6.2,复写父类成员
子类继承父类的成员属性和成员方法后,如果对其“不满意”,那么可以进行复写。(即:在子类中重新定义
同名的属性或方法即可。)
代码示例如下:
# 手机类
class Phone:seriesID = Noneproducer = "phone"def call_by_5g(self):print("5g通话")# 定义子类,复写父类成员
class MyPhone(Phone):# 复写父类的成员属性producer = "iphone"# 复写父类的成员方法def call_by_5g(self):print("*****开始******")print("使用5g网络进行通话")print("*****结束*****")phone = MyPhone()
phone.call_by_5g()print(phone.producer)
运行结果如下:
6.3,调用父类成员
一旦复写父类成员,类对象调用成员的时候就会调用复写后的新成员,如果需要使用被复写的父类的成员,需要特殊的调用方式。
语法1:
# 使用成员变量
父类名.成员变量# 使用成员方法
父类名.成员方法(self)
语法2:
# 使用成员变量
super().成员变量# 使用成员方法
super().成员方法
代码示例一:(语法1)
# 手机类
class Phone:seriesID = Noneproducer = "phone"def call_by_5g(self):print("父类方法:5g通话")# 定义子类,复写父类成员
class MyPhone(Phone):# 复写父类的成员属性producer = "iphone"# 复写父类的成员方法def call_by_5g(self):print("*****开始******")print(f"父类的厂商是:{Phone.producer}") # 调用父类成员属性Phone.call_by_5g(self) # 调用父类成员方法print("*****结束*****")phone = MyPhone()# 调用父类成员
print(f"打印父类producer:{Phone.producer}")
phone.call_by_5g()
运行结果如下:
代码示例二:(语法2)
# 手机类
class Phone:seriesID = Noneproducer = "phone"def call_by_5g(self):print("父类方法:5g通话")# 定义子类,复写父类成员
class MyPhone(Phone):# 复写父类的成员属性producer = "iphone"# 复写父类的成员方法def call_by_5g(self):print("*****开始******")print(f"父类的厂商是:{super().producer}") # 调用父类成员属性super().call_by_5g() # 调用父类成员方法(无需传入self)print("*****结束*****")phone = MyPhone()# 调用父类成员
phone.call_by_5g()
运行结果如下:
7,Python类型注解
一般,无法直接看出变量类型的时候会添加变量的类型注解。
类型注解是在代码中涉及数据交互的地方提供数据类型的显式说明。
在Pycharm中编写代码,经常会对可用的方法给出提示,这就是类型注解。如下图所示:
类型注解的主要功能在于:
- 帮助第三方IDE工具(如Pycharm)对代码进行类型推断,协助做代码提示
- 帮助开发者对变量进行类型注释,可以理解为一种备注
- 类型注解支持:变量的类型注解、方法的类型注解和返回值的类型注解
- 需要注意的是,
类型注解仅仅是提示性的,而不是决定性的
,类型注解和实际代码不同不会报错
7.1,变量的类型注解
类型注解语法一:变量:类型
类型注解语法二:通过注释进行类型注解:# type:类型
案例演示:(类型注解语法一 )
# 基础数据类型注解(实际开发中一般无需注解,因为可以看出数据的类型)
var_1:int = 10
var_2:float = 3.1415
var_3:bool = True
var_4:str = "HELLO"# 类对象类型注解
class Student:# pass关键字用于补全语法pass# stu对象是Student类型
stu: Student = Student()# 容器类型注解
my_list:list = [1,2,3]
my_tuple: tuple = (1,2,3)
my_set: set = {1,2,3}
my_dict:dict = {"1":"hello"}
my_str:str = "HELLO"
# 容器类型详细注解(Python3.9以上支持)
my_list2: list[int] = [1,2,3]
my_tuple2: tuple[int, str, bool] = (1,"Hi",True)
my_dict2: dict[str,int] = {"IT":666}
案例演示:(类型注解语法二)
import json
import random# 在注释中进行变量类型注解
var_1 = random.randint(1,10) # type:int
# json.loads()可用于将JSON 格式的字符串转换为字典
var_2 = json.loads('{"name":"Alice"}') # type:dict[str,str]
print(var_2)
def func():return 10# 标明var_3是int类型
var_3 = func() # type:int
7.2,方法的类型注解
为方法做类型注解,可以分为:为方法形参进行类型注解
和为方法返回值进行类型注解
。
方法形参类型注解语法:
def 函数方法名(形参名:类型,形参名:类型......):pass
代码示例如下:
返回值的类型注解语法:
def 函数方法名(形参:类型,......,形参:类型) ->返回值类型:pass
代码示例如下:
"""
演示对返回值进行类型注解
"""
def func(data:list) -> list: # 此处标注方法返回值为list类型return dataprint(func([1,2,3,4,5])) # 运行结果:[1, 2, 3, 4, 5]
7.3,Union联合类型注解
在某些情形下,使用普通类型注解可以很好的描述数据。示例如下:
# 如下数据,类型注解可以很好的描述
my_list:list[int] = [1,2,3]
my_dict:dict[str, int] = {"age":11,"num":3}
但某些数据,使用普通类型注解无法很好的描述,示例如下 :(各种数据类型混合在一起 )
myList = [1,2,"Hello","World"]
myDict2 = {"name":"小黄","age":11}
对于各种数据类型混装到一起的数据,就可以使用Union联合类型注解
。使用Union数据类型必须先导包。
导包:
from typing import Union
Union联合类型注解语法:
Union[类型,...,类型]
代码示例如下:
# 导包
from typing import Union# 变量的Union联合类型注解
# myList内部str和int型的数据都可以
myList:list[Union[str, int]] = [1,2,"Hello","World"]
# myDict内部的key值是str类型,value值是str或int类型都可以
myDict:dict[str, Union[str, int]] = {"name":"小黄","age":11}# 方法中使用Union联合类型注解
# 传入的参数data可以是字符串也可以是数字;返回值可以是int也可以是str
def func(data:Union[int,str]) -> Union[int,str]:# 函数体为空,使用pass关键字补全语法pass
我们在调用func函数
的时候,在Pycharm中使用快捷键ctrl+P
就可以看到参数类型的要求,如下图所示:
8,面向对象的特性:多态
多态是指多种状态。即完成某个行为(函数)时,
使用不同的对象会得到不同的状态
。
多态常作用于继承关系上。比如:
- 定义方法时通过类型注解声明接受父类对象,实际传入子类对象进行工作
- 即以父类做定义声明,以子类做实际工作,用以获得同一行为的不同状态
案例演示:
"""
演示面向对象的多态性
"""class Animal:# 定义一个方法def speak(self):passclass Dog(Animal):# 复写父类方法def speak(self):print("汪汪汪")class Cat(Animal):def speak(self):print("喵喵喵")# 制造点噪音,需要传入Animal对象
def make_noise(animal:Animal):animal.speak()# 演示多态,使用2个不同的子类对象来调用函数,获得不同的状态
dog = Dog()
cat = Cat()
make_noise(dog)
make_noise(cat)
运行结果如下:
简而言之,对象的多态性即:父类的引用指向子类的对象。
抽象类和抽象方法
抽象方法: 方法体是空实现的(pass)称之为抽象方法。
如上面代码中的Animal中的speak方法
抽象类: 含有抽象方法的类即为抽象类。如上面代码中的Animal类
- 抽象类用于做顶层设计,就好比定义一个标准,其中包含了一些抽象方法(未实现的方法)
抽象类的子类必须复写或实现父类所有的抽象方法,否则它们自己也会被视为抽象类
案例演示:
# 定义一个空调的抽象类(相当于制定标准)
class AC:def cool_wind(self):"""制冷"""passdef hot_wind(self):"""制热"""passdef swing_wind(self):"""摆风"""pass# 定义一个美的空调子类,作为空调抽象类AC的子类
class Media_AC(AC):# 子类需要复写抽象父类中的方法def cool_wind(self):print("美的空调制冷")def hot_wind(self):print("美的空调制热")def swing_wind(self):print("美的空调摆风")# 定义一个格力空调子类,作为空调抽象类AC的子类
class Gree_AC(AC):# 子类需要复写抽象父类中的方法def cool_wind(self):print("格力空调制冷")def hot_wind(self):print("格力空调制热")def swing_wind(self):print("格力空调摆风")# 制造冷风
def make_cool(ac:AC): # 需要传入的参数为AC空调对象ac.cool_wind()# 创建类对象
media_ac = Media_AC()
gree_ac = Gree_AC()
# 传入子类对象,调用make_cool函数,演示多态
make_cool(media_ac)
make_cool(gree_ac)
运行结果如下:
相关文章:

详解Python面向对象程序设计
Python面向对象程序设计 1,初识类和对象2,类的定义和使用3,构造方法4,常用的类内置方法4.1,字符串方法:__str__ 4.2,是否小于:__lt__4.3,是否小于等于:__le__…...
JS保留两位小数
方法1 var num 3.14159; var result num.toFixed(2); 方法2 toFixed(2) 返回的是字符串,需要转数字。 var num 3.14159; var result parseFloat(num.toFixed(2));...
ClickHouse集成Mysql表引擎跨服务器读表说明
MySQL表引擎 Clickhouse 上的MySQL引擎可以对存在远程MySQL服务器上的数据执行SELECT查询。 调用格式: MySQL(host:port, database, table, user, password, replace_query, on_duplicate_clause); 调用参数 host:port — MySQL 服务器地址。 database — 数据…...

【AI构思渲染】别眨眼!这些图片立马变效果图!
我只是随手一拍白模模型 AI构思渲染立马就给我生成了非常amazing的效果图 下面我来一波展示给大家欣赏欣赏 1.白模模型照片变效果图: 渲染风格包:白模-城市鸟瞰 关键词:商业建筑,车辆,精美景观 词权重:…...

多特征变量序列预测(10)基于麻雀优化算法的CEEMDAN-SSA-Transformer-BiLSTM预测模型
往期精彩内容: 时序预测:LSTM、ARIMA、Holt-Winters、SARIMA模型的分析与比较 全是干货 | 数据集、学习资料、建模资源分享! EMD变体分解效果最好算法——CEEMDAN(五)-CSDN博客 拒绝信息泄露!VMD滚动分…...

算法学习(十)—— 字符串
关于字符串操作 这类题一般是和其它算法合起来,比如模拟,双指针,动态规划或者回溯等,所以字符串相关的题目类型一般是非常非常丰富的,这里我们选取几道经典的题目进行讲解 部分OJ题详解 14. 最长公共前缀 14. 最长…...

「Mac畅玩鸿蒙与硬件16」鸿蒙UI组件篇6 - List 和 Grid 组件展示数据列表
List 和 Grid 是鸿蒙开发中的核心组件,用于展示动态数据。List 适合展示垂直或水平排列的数据列表,而 Grid 则适用于展示商品或图片的网格布局。本篇将展示如何封装组件,并通过按钮实现布局切换,提升界面的灵活性和用户体验。 关键…...

masm汇编字符输入小写转大写演示
从键盘读取一个字符变成大写换行并输出 assume cs:codecode segmentstart:mov ah,1int 21hmov bl,alsub bl,20hmov dl,10mov ah,2int 21hmov dl,blmov ah,2int 21hmov ah,4chint 21hcode ends end start 效果演示:...

防火墙|WAF|漏洞|网络安全
防火墙|WAF|漏洞|网络安全 防火墙 根据内容分析数据包: 1、源IP和目的IP地址 2、有效负载中的内容。 3、数据包协议(例如,连接是否使用 TCP/IP 协议)。 4、应用协议(HTTP、Telnet、FTP、DNS、SSH 等)。 5…...

继承机制深度解析:从基础到进阶的完整指南
文章目录 1. 继承的概念及定义1.1 继承的概念:1.2继承的定义:1.2.1 定义格式1.2.2 继承基类成员访问方式的变化: 1.3继续类模板 2. 基类和派生类间的转换2.1 向上转换(Upcasting)2.2 向下转换(Downcasting&…...

8. 数据结构——邻接表、邻接矩阵的基本操作
一、邻接表 1. 内容 2. 实现代码(直接可以复制使用) //邻接表的相关操作 #include<bits/stdc.h> #define MVnum 100 #define OK 1 #define ERROR -1 using namespace std;typedef int Status; typedef char VerTexType; //假设顶点的数据类型为char typedef int ArcT…...
OpenCV Python 版使用教程(二)摄像头调用
文章目录 一、上篇回顾二、使用步骤1. 调用摄像头的 API 介绍2. 代码示例3. 代码分析 三、下篇预告 一、上篇回顾 在上一篇中,简单介绍了如何在 Windows 和 Ubuntu 两个环境下部署和安装 OpenCV,从本篇开始将逐步介绍 OpenCV 中的常见操作。 本篇介绍 …...

基础算法——排序算法(冒泡排序,选择排序,堆排序,插入排序,希尔排序,归并排序,快速排序,计数排序,桶排序,基数排序,Java排序)
1.概述 比较排序算法 算法最好最坏平均空间稳定思想注意事项冒泡O(n)O( n 2 n^2 n2)O( n 2 n^2 n2)O(1)Y比较最好情况需要额外判断选择O( n 2 n^2 n2)O( n 2 n^2 n2)O( n 2 n^2 n2)O(1)N比较交换次数一般少于冒泡堆O( n l o g n nlogn nlogn)O( n l o g n nlogn nlogn)O( n l…...
几种常见的处理ARP欺骗的方法:静态ARP表和VLAN等
ARP(Address Resolution Protocol)欺骗是一种常见的网络攻击手段,攻击者通过伪造ARP响应,将网关的MAC地址指向攻击者的MAC地址,从而截获或篡改网络流量。为了应对ARP欺骗攻击,现代网络设备和管理员采取了一…...

突破1200°C高温性能极限!北京科技大学用机器学习合成24种耐火高熵合金,室温延展性极佳
在工程应用中,如燃气轮机、核反应堆和航空推进系统,对具备优异高温机械性能的金属合金需求十分旺盛。由于材料熔点的固有限制,传统镍基 (Ni) 高温合金的耐温能力已接近极限。为满足开发高温结构材料的需求,耐火高熵合金 (RHEAs) 于…...

ORA-00054: 资源正忙, 但指定以 NOWAIT 方式获取资源 或者超时失效
数据治理过程中,有字段长度不够,扩展字段,报:ORA-00054: 资源正忙, 但指定以 NOWAIT 方式获取资源 或者超时失效 ALTER TABLE LAPD_RSJ_CXJMYLBXCBXX MODIFY HKXZ VARCHAR2(10);错误表示当前会话在试图访问的资源(通常…...
Python学习笔记-断点操作结合异常处理
在编程中,调试和错误处理是提升代码质量和开发效率的关键环节。调试能帮助识别并修复问题,异常处理则使得程序能在出现错误时有效地管理而不至于崩溃。断点与异常处理的结合应用是高级编程中不可或缺的技巧,能够帮助更高效地定位问题,提高程序的鲁棒性。 本文将通过详细的…...

Java实现JWT登录认证
文章目录 什么是JWT?为什么需要令牌?如何实现?添加依赖:JwtUtils.java(生成、解析Token的工具类)jwt配置:登录业务逻辑:其他关联代码:测试: 什么是JWT? JWT(Json Web Token&…...

「Mac畅玩鸿蒙与硬件20」鸿蒙UI组件篇10 - Canvas 组件自定义绘图
Canvas 组件在鸿蒙应用中用于绘制自定义图形,提供丰富的绘制功能和灵活的定制能力。通过 Canvas,可以创建矩形、圆形、路径、文本等基础图形,为鸿蒙应用增添个性化的视觉效果。本篇将介绍 Canvas 组件的基础操作,涵盖绘制矩形、圆…...

山东路远生态科技有限公司竣工投产仪式暨产品发布会圆满举行
第二十届三中全会于2024年7月15日至18日在北京举行。全会审议通过了《关于进一步全面深化改革、推进中国式现代化的决定》。其中提到,“要健全因地制宜发展新质生产力体制机制”。 新质生产力是由技术革命性突破、生产要素创新性配置、产业深度转型升级而催生的当代先进生产力…...
【决胜公务员考试】求职OMG——见面课测验1
2025最新版!!!6.8截至答题,大家注意呀! 博主码字不易点个关注吧,祝期末顺利~~ 1.单选题(2分) 下列说法错误的是:( B ) A.选调生属于公务员系统 B.公务员属于事业编 C.选调生有基层锻炼的要求 D…...

pikachu靶场通关笔记22-1 SQL注入05-1-insert注入(报错法)
目录 一、SQL注入 二、insert注入 三、报错型注入 四、updatexml函数 五、源码审计 六、insert渗透实战 1、渗透准备 2、获取数据库名database 3、获取表名table 4、获取列名column 5、获取字段 本系列为通过《pikachu靶场通关笔记》的SQL注入关卡(共10关࿰…...

微软PowerBI考试 PL300-在 Power BI 中清理、转换和加载数据
微软PowerBI考试 PL300-在 Power BI 中清理、转换和加载数据 Power Query 具有大量专门帮助您清理和准备数据以供分析的功能。 您将了解如何简化复杂模型、更改数据类型、重命名对象和透视数据。 您还将了解如何分析列,以便知晓哪些列包含有价值的数据,…...

HDFS分布式存储 zookeeper
hadoop介绍 狭义上hadoop是指apache的一款开源软件 用java语言实现开源框架,允许使用简单的变成模型跨计算机对大型集群进行分布式处理(1.海量的数据存储 2.海量数据的计算)Hadoop核心组件 hdfs(分布式文件存储系统)&a…...
AGain DB和倍数增益的关系
我在设置一款索尼CMOS芯片时,Again增益0db变化为6DB,画面的变化只有2倍DN的增益,比如10变为20。 这与dB和线性增益的关系以及传感器处理流程有关。以下是具体原因分析: 1. dB与线性增益的换算关系 6dB对应的理论线性增益应为&…...
MySQL 8.0 事务全面讲解
以下是一个结合两次回答的 MySQL 8.0 事务全面讲解,涵盖了事务的核心概念、操作示例、失败回滚、隔离级别、事务性 DDL 和 XA 事务等内容,并修正了查看隔离级别的命令。 MySQL 8.0 事务全面讲解 一、事务的核心概念(ACID) 事务是…...

Linux nano命令的基本使用
参考资料 GNU nanoを使いこなすnano基础 目录 一. 简介二. 文件打开2.1 普通方式打开文件2.2 只读方式打开文件 三. 文件查看3.1 打开文件时,显示行号3.2 翻页查看 四. 文件编辑4.1 Ctrl K 复制 和 Ctrl U 粘贴4.2 Alt/Esc U 撤回 五. 文件保存与退出5.1 Ctrl …...

MySQL:分区的基本使用
目录 一、什么是分区二、有什么作用三、分类四、创建分区五、删除分区 一、什么是分区 MySQL 分区(Partitioning)是一种将单张表的数据逻辑上拆分成多个物理部分的技术。这些物理部分(分区)可以独立存储、管理和优化,…...

C++实现分布式网络通信框架RPC(2)——rpc发布端
有了上篇文章的项目的基本知识的了解,现在我们就开始构建项目。 目录 一、构建工程目录 二、本地服务发布成RPC服务 2.1理解RPC发布 2.2实现 三、Mprpc框架的基础类设计 3.1框架的初始化类 MprpcApplication 代码实现 3.2读取配置文件类 MprpcConfig 代码实现…...

简约商务通用宣传年终总结12套PPT模版分享
IOS风格企业宣传PPT模版,年终工作总结PPT模版,简约精致扁平化商务通用动画PPT模版,素雅商务PPT模版 简约商务通用宣传年终总结12套PPT模版分享:商务通用年终总结类PPT模版https://pan.quark.cn/s/ece1e252d7df...