python中抽象与类

前言:

python中所有的数据都是以对象的形式存在,无论是简单的数字类型还是复杂的代码模块。然而python特殊的语法形式巧妙的将实现对象机制的大量细节隐藏了,比如输入num = 7就可以创建一个值为7的整数对象,并且将这个对象赋值给变量num。只是这个对象包含了加法,乘法之类方法的对象。
抽象可以节省很多工作,实际上它的作用还要更大,它是使得计算机程序可以让人读懂的关键。计算机非常乐于处理精准和具体的指令,但是人就不一样,人需要简洁但不需要具体和精准

当你需要许多相似的行为,但是不同的状态时,使用对象是最好的选择

函数


  • 创建函数
    函数是可以调用,它执行某种行为并且返回一个值。一般来说,内建的callable函数可以用来判断函数是否可调用。callable( f )
  • 记录函数
    给函数写文档,加入注释或直接在def后面写上字符串
  • 位置参数:定义函数的时候括号里面的形参,位置很重要,比名字重要
  • 关键字参数:使用参数名提供的参数叫做关键字参数hello(greeting = "Hello",name = "world"),参数名和值一定要对应,关键字参数可以在函数中给参数提供默认值,提供默认值之后,在调用的时候就可以提供可以不提供了。
  • 收集位置参数(不限量):有时候让用户提供任意数量的参数,在形参之前加*,结果将以元组的形式传入进函数,==如果与其他的位置参数联用,则星号自动收集其余位置的参数。可以以元组的形式传入形参位置。
  • 收集关键字参数(不限量):在函数定义式的括号里参数前加两个星号**,然后就可以将不限数量的关键字参数以字典的形式传入函数。可以以字典的形式传入形参位置。

对象


对象:基本上可以看做数据(特性)以及由一系列可以存取,操作这些数据的方法所组成的集合(即attribute和function),使用对象代替全局变量和函数的原因有很多,最主要的原因:

  • 多态:可以对不同类的对象使用同样的操作。任何不知道对象是什么类型,但是又要对对象“做点什么”的时候,都会用到多态。可以让用户对于不知道是什么类的对象进行方法调用
  • 封装:对外部世界隐藏对象的工作细节:封装是可以不用关心对象是如何构建的而直接使用。
  • 继承:以普通的类为基础建立专门的类对象:程序员不想把同一段代码写好几次。比如已有类,但是又想建立一个非常类似的类,新的类可能只是添加几个方法。在编写新类时,又不想把旧的代码全部复制过去。

__init__和self


_init_()是python中一个特殊的函数名,用于根据类的定义创建实例对象。当你声明__init__( )方法时,第一个参数必须为self。当实例化一个对象时,在内存中实例化对象之后,会自动调用__init__()方法,将新建的对象作为self传入。
self参数指向了这个正在被创建的对象本身。

对象的创建


有两个步骤:首先构造对象,其次,初始化对象。
__new__构造对象
__init__初始化对象

基类(超类)


命名规则:Python编程社区有一个普遍认可的约定,函数用小写字母命名(另外有下划线进行强调),而类名各个单词的首字母大写。

python中的继承为超类,对个继承,就是多个超类。

  • 查看是否为子类:issubclass()
  • 查看基类:bases( )

覆盖方法(override)


方法中没有共有私有的定义

新建的子类会自动继承父类的所有信息,如果子类重新定义一个与父类同名的方法时,子类的方法就会将父类的方法覆盖掉.例如:下面的代码就会将父类的exclaim方法覆盖掉,init()同理。
但是注意一点:python不支持重载(overload)

class Car():
	def exclaim(self):
		print("im a car")

class YuGo(Car):
	def exclaim(self):
		print("dhnwdhjkewh")

增加属性,add attribute and method


变量中没有public和private的性质

属性分为两类:

  • 类属性:所有的实例共享的属性变量
    在累中定义好的变量属性,有可能在__init()方法中初始化的,有可能没有初始化的,但是对于所有的新生成的实例,他们的类属性变量都是相同的。
  • 实例对象属性:
    如果某个实例在后续的使用中需要添加新的属性变量,那就可以创建实例属性变量。在python的机制中,变量是不需要定义就可以直接使用的,所以其属性也是不需要定义的,可以直接使用。
    在添加属性的时候,如果一个方法x新增了一个属性A1,然后,在另外的一个方法y调用A1,如果先调用了x,再调用y,程序不会报错。但是当没有调用x,而先调用y,则会报错说属性不存在,只要一个实例,执行了一条语句,像下面的p1.x= 5时,他就相当于在p1中新增了一个属性(attribute),在后续的过程中就可以在p1中使用这个属性。
class Point:
pass
p1 = Point()
p2 = Point()
p1.x = 5
p1.y = 4
p2.x = 3
p2.y = 6
print(p1.x, p1.y)
print(p2.x, p2.y)
If we run this code, the two print statements at the end tell us the new attribute
values on the two objects

如上述代码,我们给两个新生成的对象,添加了两个新的属性,但是它不会,改变Point()的定义属性,当新生成一个对象c的时候,c是没有c.x,c.y的。

super从父类得到帮助

作用:

  1. 解决多继承(钻石问题)的歧义问题。
  2. 代替父类名,方便后期维护
  3. 调用父类方法可以不传参数self

上面说的是覆盖父类的方法,如果想要调用父类的方法怎么办?

class Person():
	def __init__(self,name):
		self.name = name

class EmainPerson(Person):
	def __init__(self,name,email):
		super().__init__(name)
		self.email = email

如上,在子类定义__init__()方法时,父类的__init__()方法会被覆盖。因此,在子类中,父类的初始化方法并不会自动调用,我们必须显示调用它

  • 通过super()方法获取父类Person的定义
  • 子类的__init__()调用了Person.init()方法。它会自动将self参数传递给父类。因此,你只需要传递其他参数就行,上面的例子其他参数是name
  • self.email = email这行新的代码真正起到作用将EmailPerson与Person分开

我们可以在定义EmainPerson的时候,重新定义__init__()方法如下:

class EmainPerson(Person):
	def __init__(self,name,email):
		self.name = name
		self.email = email

但是这样做有悖于使用继承的初衷,我们应该让Person完成它自己应该完成的事情,优点:当Person类的定义改变时,使用super可以保证这些改变自动修改,不用手动修改。

self自辩


C++和java在类的定义中是已经假定了有了实例的。而python没有假定,所以只有用self来代表实例对象。

self必须为类方法的第一个参数。python使用self参数找到正确的对象所包含的特性和方法。
例如:

class Car():
	def exclaim(self):
		print("im a car")

car1 = Car()
car1.exclaim()
car1.exclaim()---->Car.exclaim( car1 )
上述代码做了哪些事情?

  • 查找car对象所属的类(Car)
  • 把car对象作为self参数传递给Car类所包含的exclaim()方法。

例子:

>>> class Point:
... def reset():
... pass
...
>>> p = Point()
>>> p.reset()
Traceback (most recent call last):
File "<stdin>", line 1, in <module>
TypeError: reset() takes no arguments (1 given)

定义属性(property)的方法:修饰符


attribute译为特性(下面的name为特性),就是我们常说的对象特性,property译为属性
使用属性对特性进行访问和设置

class Duck():
	name= none
	def __init(self):
		....
		pass
	def get_name(self):
		....
		pass
	def set_name(self):
		....
		pass	
	name = property(get_name,set_name)

修饰符:定义属性的方法,
@property,用于指示getter()方法
@name.setter,用于指示setter()方法

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值