第十章 类和对象[DDT书本学习 小甲鱼]【2】

import random as r
class Fish:
def __init__(self):
self.x=r.randint(0,10)
self.y=r.randint(0,10)
def move(self):
self.x-=1
print("我的位置是:",self.x,self.y)

class Goldfish(Fish):
pass

class Carp(Fish):
pass

class Salmon(Fish):
pass

class Shark(Fish):
def _init_(self):
self.hungry=True
def eat(self):
if self.hungry:
print("吃货的梦想就是天天有的吃")
self.hungry=False
else:
print("太撑了,吃不下了!")

f=Fish()
print(f.move())
print(f.move())
s=Shark()
print(s.eat())
print(s.eat())
-------------------------------------------------
我的位置是: 2 4
我的位置是: 1 4
吃货的梦想就是天天有的吃
太撑了,吃不下了!
================================================
加入 s.move()会报错 因为子类重写__inint__覆盖了父类 s对象没有x属性
解决办法 1。调用未绑定的父类方法
2。使用super函数
1调用未绑定的父类方法,修改代码如下
class Shark(Fish):
def __init__(self):
Fish.__init__(self)#此self是子类对象
self.hungry=True
2.使用super函数(不需要指定基类名字,只需要改变继承的父类,方法更优)
class Shark(Fish):
def __init__(self):
super.__init__()
self.hungry=True
====================================================
以上两种方法都可以实现同一效果,使得s.move()可以正常使用。

11.5多重继承(同时继承多个父类的属性和方法) 缺点:容易导致代码混乱,出现BUG
class Base1:
def foo1(self):
print("我是foo1,我在Base1中。。。")
class Base2:
def foo2(self):
print("我是foo2,我在Base2中。。。")
class C(Base1,Base2):
pass
c=C()
print(c.foo1)
print(c.foo2)
-----------------------
我是foo1,我在Base1中。。。
我是foo2,我在Base2中。。。
=========================================================
11.6组合
先学习了继承,后学习了多重继承,不到必要时候不使用多重继承。
上回有了乌龟类,鱼类,现在要求一个类,叫水池,水池里要有乌龟和鱼。
使用多重继承就很奇怪,因为水池和乌龟、鱼是不同物种,如何组合成水池的类?
在Python里很简单,直接把需要的类放进去实例化就可以了,这就叫【组合】
代码如下:
class Wugui:
def __init__(self,x):
self.num=x
class Yu:
def __init__(self,x):
self.num=x
class Chi:
def __init__(self,x,y):
self.gui=Wugui(x)
self.yu=Yu(y)
def print_num(self):
print("水池里总共有乌龟%d只,小鱼%d条!"%(self.gui.num,self.yu.num))

chi=Chi(3,8)
chi.print_num()
---------------------------
水池里总共有乌龟3只,小鱼8条!
===============================================================
11.7类、类对象、实例对象
class C: 是一个类,定义完后 也就是一个类对象
count=0
a=C()
b=C()
c=C()
print(a.count)
print(b.count)
print(c.count)
------------------
0
0
0
======================修改代码如下
c.count+=10
print(c.count)
----------------
10
=======================但是,此时b.count和c.count呢?
print(a.count)
print(b.count)
print(C.count)
----------------
0
0
0
========================为何呢?接着看!
C.count+=100
print(a.count)
print(b.count)
print(c.count)
---------------
100
100
10
=============================思考原因如下
对实例对象的count属性赋值后,覆盖了类对象C的count属性。
如果没有赋值覆盖,那么引用的是类对象的count属性。
图如下
类C
类对象C
实例对象 a b c
==================================================
另外,如果属性的名字与方法名相同,属性会覆盖方法:
class C:
def x(self):
print("X-Man")
c=C()
print(c.x())
--------------
X-Man
=====================修改代码如下
c.x=1
print(c.x)
-------------
1
=======================加入代码
print(c.x())
--------------
报错,因为方法已经被属性覆盖了。
为了避免以上冲突,大家应该遵守一些约定俗成的规定
1,类的定义要“少吃多餐”,要善于利用继承和组合机制来进行扩展
2,属性命名用名词,方法名用动词且用骆驼命名法等。

猜你喜欢

转载自www.cnblogs.com/daodantou/p/10468141.html