9.3 類的繼承
編寫類時可以使用已經(jīng)編寫好的類(類似于調(diào)用)時就要用到繼承。
一個類繼承另一個類:原有的類稱為【父類】,新的類叫做【子類】。
子類將獲得父類的所有【屬性和方法】,并且子類還可以定義自己的屬性和方法;在子類中也可以修改父類中的【方法】。
1 創(chuàng)建子類的方法
下面還是以上篇中汽車的類為父類,創(chuàng)建它的子類。
#*******************這一段是之前創(chuàng)建的汽車類**********************#
class Car():
"""一次模擬汽車的簡單嘗試"""
def __init__(self, make, model, year):
"""初始化描述汽車的屬性"""
self.make = make
self.model = model
self.year = year
self.odometer_reading = 0 #這兒有必要先賦一個值,因為下面默認無實參傳遞給它
def get_descriptive_name(self):
"""返回整潔的汽車描述性信息"""
long_name = str(self.year) + ' ' + self.make + ' ' + self.model
return long_name.title()
def read_odometer(self):
"""打印一條汽車里程的信息"""
print("This car has " + str(self.odometer_reading) + " miles on it.")
def update_odometer(self, mileage):
"""
將里程表讀數(shù)設(shè)置為指定的值
并禁止將里程表的讀數(shù)往回調(diào)
"""
if mileage >= self.odometer_reading: #里程數(shù)必須 ≥ 當前的里程讀數(shù)
self.odometer_reading = mileage
else:
print("You can't roll back an odometer!")
def increment_odometer(self, miles):
"""里程表讀數(shù)增加指定的量"""
self.odometer_reading += miles
#*******************這一段是之前創(chuàng)建的汽車類**********************#
###上面的叫父類,下面我們開始創(chuàng)建它的子類 --- 電動汽車類(它屬于汽車但是又有自己的特點)
class ElectricCar(Car):
"""電動汽車的獨特之處"""
def __init__(self, make, model, year):
"""初始化父類的屬性"""
super().__init__(make, model, year)
#下面我們開始使用這個[子類]試一試
my_tesla = ElectricCar('tesla', 'model s', 2016)
print(my_tesla.get_descriptive_name())
#注意這里的get_descriptive_name()函數(shù)是從新創(chuàng)建的子類里調(diào)用的!
Result
2016 Tesla Model S
【注意點】:
①創(chuàng)建子類時父類必須包含在當前界面
②必須在子類的括號中指明父類的名稱class ElectricCar(Car):
③第一個方法__init__接受創(chuàng)建Car類所需的信息(注意這兒有self)
④super()函數(shù)是讓子類和父類連接起來,就是調(diào)用父類的【方法】__init__(注意這兒沒有self)
⑤創(chuàng)建實例的時候調(diào)用子類 --- 子類自動向父類尋找
2 當然你還可以給子類新增屬于他自己的【方法和屬性】
#*******************這一段是之前創(chuàng)建的汽車類**********************#
class Car():
"""一次模擬汽車的簡單嘗試"""
def __init__(self, make, model, year):
"""初始化描述汽車的屬性"""
self.make = make
self.model = model
self.year = year
self.odometer_reading = 0 #這兒有必要先賦一個值,因為下面默認無實參傳遞給它
def get_descriptive_name(self):
"""返回整潔的汽車描述性信息"""
long_name = str(self.year) + ' ' + self.make + ' ' + self.model
return long_name.title()
def read_odometer(self):
"""打印一條汽車里程的信息"""
print("This car has " + str(self.odometer_reading) + " miles on it.")
def update_odometer(self, mileage):
"""
將里程表讀數(shù)設(shè)置為指定的值
并禁止將里程表的讀數(shù)往回調(diào)
"""
if mileage >= self.odometer_reading: #里程數(shù)必須 ≥ 當前的里程讀數(shù)
self.odometer_reading = mileage
else:
print("You can't roll back an odometer!")
def increment_odometer(self, miles):
"""里程表讀數(shù)增加指定的量"""
self.odometer_reading += miles
#*******************這一段是之前創(chuàng)建的汽車類**********************#
###上面的叫父類,下面我們開始創(chuàng)建它的子類 --- 電動汽車類(它屬于汽車但是又有自己的特點)
class ElectricCar(Car):
"""電動汽車的獨特之處"""
def __init__(self, make, model, year):
"""
電動汽車的獨特之處
初始化父類的屬性,再初始化子類的屬性
"""
super().__init__(make, model, year)
self.battery_size = 70 #新增的子類屬性,需要初始化
#下面我們開始創(chuàng)建新的方法來表述這個電瓶的相關(guān)信息
def describe_battery(self):
"""打印一條描述電瓶容量的消息"""
print("This car has a " + str(self.battery_size) + "-KWh battery.")
#下面我們利用新的方法創(chuàng)建實例
my_tesla = ElectricCar('tesla', 'model s', 2016)
print(my_tesla.get_descriptive_name()) #用于返回整潔的信息
my_tesla.describe_battery() #調(diào)用新的方法describe_battery()
Result:
2016 Tesla Model S
This car has a 70-KWh battery.
3 還可以更改父類已有的方法
#*******************這一段是之前創(chuàng)建的汽車類**********************#
class Car():
"""一次模擬汽車的簡單嘗試"""
def __init__(self, make, model, year):
"""初始化描述汽車的屬性"""
self.make = make
self.model = model
self.year = year
self.odometer_reading = 0 #這兒有必要先賦一個值,因為下面默認無實參傳遞給它
def get_descriptive_name(self):
"""返回整潔的汽車描述性信息"""
long_name = str(self.year) + ' ' + self.make + ' ' + self.model
return long_name.title()
def read_odometer(self):
"""打印一條汽車里程的信息"""
print("This car has " + str(self.odometer_reading) + " miles on it.")
def update_odometer(self, mileage):
"""
將里程表讀數(shù)設(shè)置為指定的值
并禁止將里程表的讀數(shù)往回調(diào)
"""
if mileage >= self.odometer_reading: #里程數(shù)必須 ≥ 當前的里程讀數(shù)
self.odometer_reading = mileage
else:
print("You can't roll back an odometer!")
def increment_odometer(self, miles):
"""里程表讀數(shù)增加指定的量"""
self.odometer_reading += miles
#*******************這一段是之前創(chuàng)建的汽車類**********************#
###上面的叫父類,下面我們開始創(chuàng)建它的子類 --- 電動汽車類(它屬于汽車但是又有自己的特點)
class ElectricCar(Car):
"""電動汽車的獨特之處"""
def __init__(self, make, model, year):
"""
電動汽車的獨特之處
初始化父類的屬性,再初始化子類的屬性
"""
super().__init__(make, model, year)
self.battery_size = 70 #新增的子類屬性,需要初始化
#下面我們開始創(chuàng)建新的方法來表述這個電瓶的相關(guān)信息
def describe_battery(self):
"""打印一條描述電瓶容量的消息"""
print("This car has a " + str(self.battery_size) + "-KWh battery.")
#更改父類已有的屬性(重新定義即可) --- 假設(shè)父類有 fill_gas_tank這一方法
def fill_gas_tank(self):
"""電動汽車沒有油箱"""
print("This car doesn't need a gas tank!")
#開始創(chuàng)建實例 --- 假設(shè)調(diào)用了方法fill_gas_tank
my_tesla = ElectricCar('tesla', 'model s', 2016)
print(my_tesla.get_descriptive_name()) #用于返回整潔的信息
my_tesla.describe_battery() #調(diào)用新的方法describe_battery()
my_tesla.fill_gas_tank() #假設(shè)我們調(diào)用了fill_gas_tank方法查看油箱信息
【子類既可以新增也可以修改】就是繼承可以對父類 --- 取其精華,去其糟粕
Result:
2016 Tesla Model S
This car has a 70-KWh battery.
This car doesn't need a gas tank!
4 有時候類中的【方法】太多,總會讓人不想看下去,為此可以將類的一部分提取出來作為新的類——意思就是再細分類。
例如將ElectricCar類中的關(guān)于電池的一些方法劃分成一個新類 --- Battery類
#*******************這一段是之前創(chuàng)建的汽車類**********************#
class Car():
"""一次模擬汽車的簡單嘗試"""
def __init__(self, make, model, year):
"""初始化描述汽車的屬性"""
self.make = make
self.model = model
self.year = year
self.odometer_reading = 0 #這兒有必要先賦一個值,因為下面默認無實參傳遞給它
def get_descriptive_name(self):
"""返回整潔的汽車描述性信息"""
long_name = str(self.year) + ' ' + self.make + ' ' + self.model
return long_name.title()
def read_odometer(self):
"""打印一條汽車里程的信息"""
print("This car has " + str(self.odometer_reading) + " miles on it.")
def update_odometer(self, mileage):
"""
將里程表讀數(shù)設(shè)置為指定的值
并禁止將里程表的讀數(shù)往回調(diào)
"""
if mileage >= self.odometer_reading: #里程數(shù)必須 ≥ 當前的里程讀數(shù)
self.odometer_reading = mileage
else:
print("You can't roll back an odometer!")
def increment_odometer(self, miles):
"""里程表讀數(shù)增加指定的量"""
self.odometer_reading += miles
#**********************以下是單獨的電池類*************************#
class Battery():
"""一次模擬電動汽車電瓶的簡單嘗試"""
def __init__(self, battery_size=70):#初始化形參的值時最好不要加空格!
"""初始化電瓶的屬性""" #在這里我們定義了一個可選形參battery_size
self.battery_size = battery_size
def describe_battery(self):
"""打印一條描述電池容量的信息"""
print("This car has a " + str(self.battery_size) + "-KWh batttery.")
#************************以下是子類****************************#
class ElectricCar(Car):
"""電動汽車的獨特之處"""
def __init__(self, make, model, year):
"""
電動汽車的獨特之處
初始化父類的屬性,再初始化子類的屬性
"""
super().__init__(make, model, year)
self.battery = Battery() #****直接將 Battery類作為其中的一個[方法]****#
#開始創(chuàng)建實例
my_tesla = ElectricCar('tesla', 'model s', 2016)
print(my_tesla.get_descriptive_name()) #用于返回整潔的信息
my_tesla.battery.describe_battery()
#調(diào)用battery就是調(diào)用類 Battery,Battery再調(diào)用其中的describe_battery()來描述電瓶
Result:
2016 Tesla Model S
This car has a 70-KWh batttery.
5 下面再給Battery類添加一個【方法】,使它能夠根據(jù)電池容量大小報告可行駛的里程數(shù)。
#*******************這一段是之前創(chuàng)建的汽車類**********************#
class Car():
"""一次模擬汽車的簡單嘗試"""
def __init__(self, make, model, year):
"""初始化描述汽車的屬性"""
self.make = make
self.model = model
self.year = year
self.odometer_reading = 0 #這兒有必要先賦一個值,因為下面默認無實參傳遞給它
def get_descriptive_name(self):
"""返回整潔的汽車描述性信息"""
long_name = str(self.year) + ' ' + self.make + ' ' + self.model
return long_name.title()
def read_odometer(self):
"""打印一條汽車里程的信息"""
print("This car has " + str(self.odometer_reading) + " miles on it.")
def update_odometer(self, mileage):
"""
將里程表讀數(shù)設(shè)置為指定的值
并禁止將里程表的讀數(shù)往回調(diào)
"""
if mileage >= self.odometer_reading: #里程數(shù)必須 ≥ 當前的里程讀數(shù)
self.odometer_reading = mileage
else:
print("You can't roll back an odometer!")
def increment_odometer(self, miles):
"""里程表讀數(shù)增加指定的量"""
self.odometer_reading += miles
#**********************以下是單獨的電池類*************************#
class Battery():
"""一次模擬電動汽車電瓶的簡單嘗試"""
def __init__(self, battery_size=70):#初始化形參的值時最好不要加空格!
"""初始化電瓶的屬性""" #在這里我們定義了一個[可選]形參battery_size
self.battery_size = battery_size
def describe_battery(self):
"""打印一條描述電池容量的信息"""
print("This car has a " + str(self.battery_size) + "-KWh batttery.")
def get_range(self):
"""打印一條消息,指出電瓶的續(xù)航里程數(shù)"""
if self.battery_size == 70:
range = 240
elif self.battery_size == 85: #elif后是必須加條件的
range = 270
message = "This car can go approximately " + str(range)
message += " miles on a full charge." #字符串的連接方式
print(message)
#************************以下是子類****************************#
class ElectricCar(Car):
"""電動汽車的獨特之處"""
def __init__(self, make, model, year):
"""
電動汽車的獨特之處
初始化父類的屬性,再初始化子類的屬性
"""
super().__init__(make, model, year)
self.battery = Battery() #****直接將 Battery類作為其中的一個[方法]****#
#開始創(chuàng)建實例
my_tesla = ElectricCar('tesla', 'model s', 2016)
print(my_tesla.get_descriptive_name()) #用于返回整潔的信息
my_tesla.battery.describe_battery()
my_tesla.battery.get_range()
【注意最后調(diào)用的時】:
get_range( )函數(shù)在Battery類里的,在ElectricCar類里已經(jīng)將Battery類作為了其一個方法——self.battery = Battery( ),所以可以直接調(diào)用battery( )
Result:
2016 Tesla Model S
This car has a 70-KWh batttery.
This car can go approximately 240 miles on a full charge.
6 動手試一試 --- 冰淇淋小店
#**********************以下是餐館的類**********************#
class Restaurant():
"""餐館的簡介"""
def __init__(self, restaurant_name, cuisine_type):
"""初始化餐館的屬性name和type"""
self.name = restaurant_name #注意后面的名稱是形參 --- 這里是初始化的形參
self.type = cuisine_type #用self,使下面的所有方法都可使用初始化的形參
def describe_restaurant(self):
"""描述餐館的信息"""
print(self.name.title() + " is the type of " + self.type +'.')
def open_restaurant(self):
"""餐館營業(yè)時間"""
print(self.name.title() + " is open from 8 am to 10 PM.\n" )
#**********************下面嘗試編寫其子類**********************#
class IceCreamStand(Restaurant):
"""冰淇淋小店重現(xiàn)"""
def __init__(self, restaurant_name, cuisine_type):
"""初始化父類的屬性"""
super().__init__(restaurant_name, cuisine_type) #用super()函數(shù)連接父類
self.icecream_flavors = [
'original',
'chocolate',
'mocha',
'strawberry'
]
#現(xiàn)在這個子類具有了父類的所有方法和屬性,讓我們來增加一些方法
def flavors(self):
"""顯示冰淇淋的口味列表"""
print("It has the following tastes icecream:")
for icecream_flavor in self.icecream_flavors:
print(icecream_flavor)
#************************下面創(chuàng)建實例***********************#
restaurant = IceCreamStand('cold-drink shop', 'fruity')
#先調(diào)用父類的方法試試
restaurant.describe_restaurant()
restaurant.open_restaurant()
#下面調(diào)用子類新增的方法
restaurant.flavors()
Result:
Cold-Drink Shop is the type of fruity.
Cold-Drink Shop is open from 8 am to 10 PM.It has the following tastes icecream:
original
chocolate
mocha
strawberry
【在初始化的時候要特別注意 】:
1.super().__init__(形參1 ,形參2)的形式 —— 與父類連接
2.子類新增方法時,要現(xiàn)在初始化代碼下”聲明“ —— self.icecream_flavors = ...
3.在使用屬性時候要加self—— for icecream_flavor in self.icecream_flavors:
最后也想不起來說啥,看到的就提前祝你豬(* ̄(oo) ̄)年大吉吧!

7df9446e6c0aee5a4cea61e984bb2ad6.jpg