iis服务器助手广告广告
返回顶部
首页 > 资讯 > 后端开发 > Python >Python类的定义继承调用方法有哪些
  • 931
分享到

Python类的定义继承调用方法有哪些

2023-07-02 12:07:00 931人浏览 泡泡鱼

Python 官方文档:入门教程 => 点击学习

摘要

这篇文章主要讲解了“python类的定义继承调用方法有哪些”,文中的讲解内容简单清晰,易于学习与理解,下面请大家跟着小编的思路慢慢深入,一起来研究和学习“Python类的定义继承调用方法有哪些”吧!一、类的约束# _开头:&nbs

这篇文章主要讲解了“python类的定义继承调用方法有哪些”,文中的讲解内容简单清晰,易于学习与理解,下面请大家跟着小编的思路慢慢深入,一起来研究和学习“Python类的定义继承调用方法有哪些”吧!

    一、类的约束

    # _开头: 私有变量;# __开问: 私有变量,不能被继承;# __xxx__: 能被访问,不能被继承;class A:def __init__(self):self._internal = 0 # 私有变量不能被访问self.public = 1 # 可被访问def public_method(self):passdef _private_method(self): # 私有方法不能被访问passclass B:def __init__(self):self.__private = 0 # 这个属性会在内存中被重新命名为_B__privatedef __private_method(self): # 不能被访问,不能被继承passdef __private_method__(self): # 能被访问,不能被继承pass

    二、类的定义

    2.1、创建创建

    class Dog:a = "0"; #相当于public static变量,全局的"""__init__是一个默认的方法,且self为默认的,用self修饰的属性为public类型的类变量"""def __init__(self, name, age):self.name = nameself.age = ageself.sex = "1";#设置属性默认值def sit(self):print(self.name + "is now sitting" + "and sex is " + self.sex + Dog.a)@claSSMethoddef user_name(cls, name): #注意这种注解的用法return cls()dog = Dog("kk", 12);dog.sit()
    2.1.1、类的导入

    在python中分为文件、模块、类,其中文件和模块可划等价;所以导入有几种方式,比如dog.py文件中定义了两个Class,则在使用类中导入方法有以下几种:

    • from car import Dog;#导入一个模块中的特定类,使用时则直接Car();

    • import car;#导入一个模块中的所有类,使用时则需要car.Car();

    • from car import *;#不推荐,容易引起命名冲突问题

    from collections import OrderedDict; #使用标准类库t = OrderedDict();
    2.1.2、构造器
    class Date:# Primary constructordef __init__(self, year, month, day):self.year = yearself.month = monthself.day = day# Alternate constructor@classmethoddef today(cls):t = time.localtime() #它接收一个class作为第一个参数,它被用来创建并返回最终的实例, 这个cls==__init__return cls(t.tm_year, t.tm_mon, t.tm_mday)a = Date(2020, 5, 10) # Primaryb = Date.today() # Alternate

    减少构造函数的参数个数:

    class Structure1:# Class variable that specifies expected fields_field_list = []def __init__(self, *args):if len(args) != len(self._field_list):raise TypeError(f'Expected {len(self._field_list)} arguments')# Set the argumentsfor name, value in zip(self._field_list, args):setattr(self, name, value)# Example class definitionsclass Course(Structure1):# 这行只是为了一个准许入判断,没有太多实际意思,或是一个声明_field_list = ['course_name', 'total_class', 'score']c = Course('python', 30, 0.3);

    关键字参数

    class Structure2:_field_list = []def __init__(self, *args, **kwargs):if len(args) > len(self._field_list):raise TypeError(f'Expected {len(self._field_list)} arguments')# Set all of the positional argumentsfor name, value in zip(self._field_list, args):setattr(self, name, value)# Set the remaining keyWord arguments#是通过pop这种方式来检查的,在长度范围内如果pop出错则抛异常for name in self._field_list[len(args):]:setattr(self, name, kwargs.pop(name))# Check for any remaining unknown argumentsif kwargs:raise TypeError(f"Invalid argument(s): {','.join(kwargs)}")# Example useclass Course(Structure2):_field_list = ['course_name', 'total_class', 'score']course_1 = Course('python', 30, 0.3)course_2 = Course('python', 30, score=0.3)course_3 = Course('python', total_class=30, score=0.3)

    扩展关键字参数:

    class Structure3:# Class variable that specifies expected fields_field_list = []def __init__(self, *args, **kwargs):if len(args) != len(self._field_list):raise TypeError(f'Expected {len(self._field_list)} arguments')# Set the argumentsfor name, value in zip(self._field_list, args):setattr(self, name, value)# Set the additional arguments (if any)extra_args = kwargs.keys() - self._field_listfor name in extra_args:setattr(self, name, kwargs.pop(name))if kwargs:raise TypeError(f"Duplicate values for {','.join(kwargs)}")# Example useif __name__ == '__main__':class Course(Structure3):_field_list = ['course_name', 'total_class', 'score']course_1 = Course('python', 30, 0.3)course_2 = Course('python', 30, 0.3, date='8/5/2020')
    2.1.3、类属性

    要创建一个新的实例属性,可以通过描述器的形式来定义它的功能,一个描述器就是一个实现了3个核心属性访问操作的类,分别对应get\set\delete这三个特殊的方法。

    # Descriptor attribute for an integer type-checked attributeclass Integer:def __init__(self, name):self.name = name"""下面三个方法只是一个更严格的定义,可以不需要,要使用上面的描述器,需要把描述器放入到一个class中,这样所有对描述器的访问都会被get/set/delete所捕获"""def __get__(self, instance, cls):if not instance:return selfelse:return instance.__dict__[self.name]def __set__(self, instance, value):if not isinstance(value, int):raise TypeError('Expected an int object')instance.__dict__[self.name] = valuedef __delete__(self, instance):del instance.__dict__[self.name]

    示例1:

    class Point:"""实例变量,和下面的x,y不是一回事"""x = Integer('x')y = Integer('y')def __init__(self, x, y):self.x = xself.y = yprint(Point.x.name) # xpoint = Point(3, 5)print(f'point x = {point.x}') #3print(f'point y = {point.y}') #5point.y = 6print(f'after change,point y = {point.y}') #6

    三、类的继承

    ptyhon在实现继承时会用一个叫MRO列表的算法实现,它有三条规则:1、子类会先于父类;2、多个父类会根据它们在列表中的顺序被检查;3、如果对下一个类有两个合法的选择,则返回第一个合法的父类;

    3.1、单继承

    class A:def __init__(self):self.x = 0class B(A):def __init__(self):super().__init__() #这行需要注意,也可以不写,但不写时就不会调用父类的init方法self.y = 1

    3.2、多继承

    class Base:def __init__(self):print('call Base.__init__')class A(Base):def __init__(self):Base.__init__(self)print('call A.__init__')class B(Base):def __init__(self):Base.__init__(self)print('call B.__init__')"""多继承的实现"""class C(A,B):def __init__(self):A.__init__(self)B.__init__(self)print('call C.__init__')c = C()# call Base.__init__# call A.__init__# call Base.__init__# call B.__init__# call C.__init__

    3.3、调用父类方法

    class Proxy:def __init__(self, obj):self._obj = objdef __getattr__(self, name):return getattr(self._obj, name)def __setattr__(self, name, value):if name.startswith('_'):"""调用父类方法"""super().__setattr__(name, value)else:setattr(self._obj, name, value)proxy = Proxy({})proxy.__setattr__("_name", "hm")

    3.4、属性扩展

    3.4.1、完全扩展
    # 父类class Person:def __init__(self, name):self.name = name# defined Getter function, auto to call the sign name.setter when it be build@propertydef name(self):return self._name# defined Setter function@name.setterdef name(self, value):if not isinstance(value, str):raise TypeError('Expected a string')self._name = value# defined Deleter function@name.deleterdef name(self):raise AttributeError("Can't delete attribute")"""子类"""class SubPerson(Person):@propertydef name(self):print('Getting name')return super().name@name.setterdef name(self, value):print(f'Setting name to {value}')super(SubPerson, SubPerson).name.__set__(self, value)@name.deleterdef name(self):print('Deleting name')super(SubPerson, SubPerson).name.__delete__(self)"""测试"""sub_person = SubPerson('Guido')print(f'name is: {sub_person.name}')
    3.4.2、单独扩展
    class SubPerson(Person):@Person.name.getterdef name(self):print('Getting name')return super().name # or super(SubPerson, SubPerson).name.__set__(self, value)sub_p = SubPerson('Bill')
    #不能用property的原因是,property其实是get、set、del函数的集合,各有各的用处。下面才是正确的扩展方式,所以下面的代码是不工作的class SubPerson(Person):@property # Doesn't workdef name(self):print('Getting name')return super().name#如果要用property属性则要用下面的编码实现class SubPerson(Person):@propertydef name(self):print('Getting name')return super().name@name.setterdef name(self, value):print(f'Setting name to {value}')super(SubPerson, SubPerson).name.__set__(self, value)@name.deleterdef name(self):print('Deleting name')super(SubPerson, SubPerson).name.__delete__(self)

    四、类的调用

    import timeclass Date:# Primary constructordef __init__(self, year, month, day):self.year = yearself.month = monthself.day = day# Alternate constructor@classmethoddef today(cls):t = time.localtime() #它接收一个class作为第一个参数,它被用来创建并返回最终的实例, 这个cls==__init__return cls(t.tm_year, t.tm_mon, t.tm_mday)
    """普通调用"""c = Date(2010, 12, 12)"""类方法在继承中使用"""class NewDate(Date):passc = Date.today() # Creates an instance of Date (cls=Date)d = NewDate.today() # Creates an instance of NewDate (cls=NewDate)

    五、抽象类

    from abc import ABCMeta, abstractmethodclass IStream(metaclass=ABCMeta):@abstractmethoddef read(self, max_bytes=-1):pass@abstractmethoddef write(self, data):pass"""不能被实例化"""#a = IStream()class SocketStream(IStream):def read(self, max_bytes=-1):passdef write(self, data):pass"""检查"""def serialize(obj, stream):if not isinstance(stream, IStream):raise TypeError('Expected an IStream')pass

    5.1、强制类型检查

    from abc import ABCMeta, abstractmethodclass IStream(metaclass=ABCMeta):@abstractmethoddef read(self, max_bytes=-1):pass@abstractmethoddef write(self, data):passimport io# ReGISter the built-in I/O classes as supporting our interfaceIStream.register(io.IOBase)# Open a nORMal file and type checkf = None #open('test.txt')print(f'f object is IStream type: {isinstance(f, IStream)}')#f object is IStream type: False

    六、类的比较

    from functools import total_orderinGClass Room:def __init__(self, name, length, width):self.name = nameself.length = lengthself.width = widthself.square_feet = self.length * self.width@total_orderingclass House:def __init__(self, name, style):self.name = nameself.style = styleself.rooms = list()@propertydef living_space_footage(self):return sum(r.square_feet for r in self.rooms)def add_room(self, room):self.rooms.append(room)def __str__(self):return f'{self.name}: {self.living_space_footage} square foot {self.style}'def __eq__(self, other):return self.living_space_footage == other.living_space_footagedef __lt__(self, other):return self.living_space_footage < other.living_space_footage# Build a few houses, and add rooms to themh2 = House('h2', 'Cape')h2.add_room(Room('Master Bedroom', 14, 21))h2.add_room(Room('Living Room', 18, 20))h2.add_room(Room('Kitchen', 12, 16))h2.add_room(Room('Office', 12, 12))h3 = House('h3', 'Ranch')h3.add_room(Room('Master Bedroom', 14, 21))h3.add_room(Room('Living Room', 18, 20))h3.add_room(Room('Kitchen', 12, 16))h4 = House('h4', 'Split')h4.add_room(Room('Master Bedroom', 14, 21))h4.add_room(Room('Living Room', 18, 20))h4.add_room(Room('Office', 12, 16))h4.add_room(Room('Kitchen', 15, 17))houses = [h2, h3, h4]print(f'Is {h2} bigger than {h3}: {h2 > h3}')print(f'Is {h3} smaller than {h4}: {h3 < h4}')print(f'Is {h3} greater than or equal to {h2}: {h3 >= h2}')print(f'Which one is biggest in houses: {max(houses)}')print(f'Which is smallest in houses: {min(houses)}')""""""# Is h2: 990 square foot Cape bigger than h3: 846 square foot Ranch: True# Is h3: 846 square foot Ranch smaller than h4: 1101 square foot Split: True# Is h3: 846 square foot Ranch greater than or equal to h2: 990 square foot Cape: False# Which one is biggest in houses: h4: 1101 square foot Split# Which is smallest in houses: h3: 846 square foot Ranch# """"""class House:def __eq__(self, other):passdef __lt__(self, other):pass# Methods created by @total_ordering__le__ = lambda self, other: self < other or self == other__gt__ = lambda self, other: not (self < other or self == other)__ge__ = lambda self, other: not (self < other)__ne__ = lambda self, other: not self == other

    感谢各位的阅读,以上就是“Python类的定义继承调用方法有哪些”的内容了,经过本文的学习后,相信大家对Python类的定义继承调用方法有哪些这一问题有了更深刻的体会,具体使用情况还需要大家实践验证。这里是编程网,小编将为大家推送更多相关知识点的文章,欢迎关注!

    --结束END--

    本文标题: Python类的定义继承调用方法有哪些

    本文链接: https://www.lsjlt.com/news/341766.html(转载时请注明来源链接)

    有问题或投稿请发送至: 邮箱/279061341@qq.com    QQ/279061341

    本篇文章演示代码以及资料文档资料下载

    下载Word文档到电脑,方便收藏和打印~

    下载Word文档
    软考高级职称资格查询
    编程网,编程工程师的家园,是目前国内优秀的开源技术社区之一,形成了由开源软件库、代码分享、资讯、协作翻译、讨论区和博客等几大频道内容,为IT开发者提供了一个发现、使用、并交流开源技术的平台。
    • 官方手机版

    • 微信公众号

    • 商务合作