【发布时间】:2016-01-05 00:01:42
【问题描述】:
我对 python 有疑问。 我阅读了 2 本手册来学习这门语言(儿童 Python 和艰难学习 Python),现在我正试图了解 OOP 的工作原理以及如何使用它。
我想创建一个简单的脚本来学习如何处理类和方法:
脚本应该允许用户查看他在冰箱里有什么,每个物品都有一个数量和一个名称。用户应该能够做的其他事情是:添加项目、修改其名称或数量以及从“目录”中删除项目。
我尝试使用 OOP 设计来实现它,因为那是我想学习的。 问题是列表的 append() 和 remove() 方法的行为不同,即使被调用来处理同一个对象。
这是代码。我确信我在属性、参数和方法方面做错了,因为这是最让我困惑和让我对 OOP 感到疯狂的地方
class Item:
def __init__(self, name, qty='1'):
self.name = name
self.qty = qty
class Fridge:
def __init__(self):
#create a Fridge object that is a list of stuff
self.items = []
#append to the list (fridge) an Item
def add_item(self, name, qty='1'):
self.items.append(Item(name))
def modify_item(self):
pass
def remove_item(self,name, qty='0'):
#from the items list remove Item(name))
self.items.remove(Item(name))
当我在 shell 中使用 name 和 qty 参数调用 add_item 方法时,该函数实际上将项目添加到列表中。当我尝试删除 Item 它说:
Traceback (most recent call last):
File "<pyshell#164>", line 1, in <module>
f.remove_item('orange')
File "C:/Users/Utente.1/Desktop/python projects/OOP/chap2 modules - packages/drill - frigorifero/fridge.py", line 22, in remove_item
self.items.remove(Item(name))
ValueError: list.remove(x): x not in list
但是f.items[0].name 返回
'orange' 作为一个值。所以'orange' 存在并且存在,因为f.add_item('orange') 方法有效,但是当我使用f.remove_item('orange') 方法时我无法删除它。
怎么了?你能解释一下我的错误,还有你认为我缺少什么,而不是了解 OOP 以及如何改进它?在我看来,它就像一个迷宫。
【问题讨论】:
-
为什么将数量存储为字符串?
-
对设计的一个评论,我会尝试在概念上将项目定义和计数分开。我的意思是我会以某种方式定义项目,然后保留某种数据类型来跟踪其中有多少。例如,我会将项目存储为字典键,并使字典值对应于项目计数。通过这种方式,我们可以从项目的类型中获取有关有多少项目的数据。在这种情况下,我发现命名有点混乱,因为
Item具有项目的类型 和 有关同一类中有多少项目的信息... -
... 您可以将该行为封装到一个类中,并提供让您访问该类的方法,而无需将底层机制/机器暴露给您的类的最终用户。来自 Martijn Pieters 的 answer 为您提供了一个很好的建议,说明如何使用存储信息的基础列表来做到这一点。请记住,如果您的设计正确,您也可以将其更改为使用其他数据结构,而最终用户不知道他们正在使用您提供的
remove_item等方法。 -
你完全正确!这是我对 OOP 的第一次尝试,我真的很难理解事物并做出任何有意义的事情。所以我应该用字典替换列表?
-
好吧,您也许可以这样做,但您不一定必须这样做。从 OOP 设计的角度来看,更大的问题是您尝试以这样一种方式编写代码,即如果您在内部更改为不同的数据结构,您的类代码的用户将不必知道更改。本质上,如果你做得正确,你可以改变你的实现,而最终用户不必更改他们的代码,这就是人们谈论封装时的意思。
标签: python class oop methods parameters