组合关系
组合关系也是关联关系的一种特例,同样体现整体与部分的关系,这种关系比聚合更强
- 代表contains-a的关系
- 在组合的关系中,彼此依赖的,不可分割
- 具有相同的生命周期,整体被销毁,部分也会被销毁
代码:从代码上看,与聚合相同,只能 从语义区分
比如手机和零件的关系,手机是整体,部分是cpu、屏幕、ram、rom,部分之间是不同的。
案例
在上面的购物车代码中,_goods_dict是dict类型,内部还有dict类型的数据,不够优雅,在本例中对购物车代码进行优化
图中所示,Cart类的_cartitems是list类型,元素是CartItem类对象,CartItem类的_goods是Goods类对象
Cart类和CartItem类就是组合关系,CartItem和Goods是依赖关系
练习
根据UML类图改造上篇文章的购物车代码:
商品类
class Goods:
def __init__(self,id,name,price):
#商品编号
self._id=id
self._name=name
self._price=price
def get_id(self):
return self._id
def get_name(self):
return self._name
def get_price(self):
return self._price
购物车项目类
class CartItem:
def __init__(self,goods,num):
self._goods=goods
self._num=num
def add_num(self):
self._num+=1
def minus_num(self):
self._num-=1
def get_num(self):
return self._num
def get_goods_id(self):
return self._goods.get_id()
def get_goods(self):
return self._goods
购物车类
class Cart:
def __init__(self):
#key是商品编号,value是dict类型的序列,其中key是goods,value是goods对象,key是num,value是数量
self._cartitems=[]
#购物车中总共的数量
self._total_num=0
self._total_price=0
def add_goods(self,goods):
index=self._has_goods(goods)
if index>=0:
cartitem=self._cartitems[index]
cartitem.add_num()
else:
cartitem=CartItem(goods,1)
self._cartitems.append(cartitem)
self._total_num+=1
self._total_price+=goods.get_price()
#伪私有方法,判断商品是否存在,存在返回索引值,不存在返回-1
def _has_goods(self,goods):
id=goods.get_id()
for index,item in enumerate(self._cartitems):
if id==item.get_goods_id():
return index
return -1
def remove_goods(self,goods):
index=self._has_goods(goods)
#如果存在
if index>=0:
cartitem=self._cartitems[index]
#判断数量是1,就移除
if cartitem.get_num()==1:
del self._cartitems[index]
else:
cartitem.minus_num()
self._total_num-=1
self._total_price-=goods.get_price()
def get_total_price(self):
return self._total_price
def get_total_num(self):
return self._total_num
def get_cartitems(self):
return tuple(self._cartitems)
测试调用
def print_info():
print("购物车数量:%d,品类:%d,数量:%d,总价:%d,商品:"%(cart.get_total_num(),len(cart.get_cartitems()),cart.get_total_num(),cart.get_total_price()),end="")
for item in cart.get_cartitems():
print("id:%s,name:%s,price:%d,num:%s||"%(item.get_goods().get_id(),item.get_goods().get_name(),item.get_goods().get_price(),item.get_num() ),end=",")
print()
cdb=Goods("001","小米充电宝",100)
dnb=Goods("002","小米电脑包",200)
dnb2=Goods("002","小米电脑包",200)
dnb3=Goods("003","小米电脑包",300)
cart=Cart()
cart.add_goods(cdb)
print_info()
cart.add_goods(dnb)
print_info()
cart.add_goods(dnb2)
print_info()
cart.add_goods(dnb3)
print_info()
cart.remove_goods(dnb2)
print_info()
cart.remove_goods(dnb2)
print_info()
聚合与组合的异同
整体和部分
聚合:整体包含很多个部分,但这里的部分都是相同的。
组合:部分和整体的关系表现为,整体包含该部分,但也包含其他部分,其他部分和该部分并不相同。
生命周期
聚合:拥有各自的生命周期
组合:拥有相同的生命周期
依赖程度
聚合:弱
组合:强
实现关系
抽象类、实现类是java中的概念,在python中也做了借鉴,这里只做介绍。
抽象类:是定义类的行为,定义空方法
实现类:一个类继承某个抽象类后,必须实现该抽象类的所有方法
总结:
- 继承和实现是类与类之间的纵向关系
- 关联是类与类之间的横向关系
- 类与类之间的关系从弱到强依次为:
依赖 < 关联 < 聚合 < 组合

