【问题标题】:Encapsulation and constraining in PythonPython中的封装和约束
【发布时间】:2021-03-02 09:27:38
【问题描述】:

我有这个测试程序:

class BankAccount:
     def __init__(self, name, balance):
         self.name = name
         self.balance = balance
         self.transaction_fee = 5.00
     def deposit(self, amount):
        self.balance = self.balance + amount
     def withdraw(self, amount):
        self.balance = self.balance - amount

我通过以下方式封装了余额、姓名和交易费用:

class BankAccount:
     def __init__(self, name, balance):
         self._name = name
         self._balance = balance
         self._transaction_fee = 5.00
     def deposit(self, amount):
        self._balance = self._balance + amount
     def withdraw(self, amount):
        self.balance = self.balance - amount

现在我需要修改 BankAccount 类以强制执行帐户余额永远不会变为负数的不变量。这意味着您应该禁止负存款,禁止超过账户余额的提款。

我曾想过在存款和取款功能中使用 if/else 语句。例如:

 def deposit(self, amount):
    if amount >= 0:
          self._balance = self._balance + amount
    else ?????

else部分,我不知道如何让它回到函数并再次要求一个合适的值。

还有其他方法可以做到这一点吗?

谢谢

【问题讨论】:

  • 如果您在 deposit() 方法中强制执行非负金额,那么您不需要 else:。如果您在 deposit() 之外强制执行此操作,那么您可以对此采取一些措施。

标签: python python-3.x oop encapsulation


【解决方案1】:

解决此问题的一种方法是为此模块定义一个异常类(例如AccountError)并引发该异常以防有人试图存入负数(或做任何其他不允许的事情)。

在调用deposit() 方法的地方,您可以捕获异常(在try-except-block 的帮助下)并允许用户在输入无效值时重试。

它可能看起来像这样:

class AccountError(Exception):
    """Module specific error"""


class BankAccount:
    ...
    ...
    ...
    def deposit(self, amount):
        if amount >= 0:
            self._balance = self._balance + amount
        else:
            raise AccountError("Deposit amount cannot be negative")

(当然,您可以向异常添加更多信息和功能。)

在调用代码的地方:

account = BankAccount()
...
...
try:
    account.deposit(negative_amount)
except AccountError as exc:
    # Code that allows you to retry the deposit.
    # Implementation depends on your program structure.

整个块可以嵌入到 forwhile 循环中,并进行一定数量的重试,或者在你的情况下任何有意义的事情。

具体的实现将取决于您的程序的结构和功能。

【讨论】:

    【解决方案2】:

    在您的方法中,您可以返回一个指示成功或失败的布尔值。然后调用代码就可以适当的处理了。

    如果您担心调用代码可能会忽略返回值并且事务静默失败,您可以改为引发异常并让调用代码来处理它 - 如下所示:

    class BankAccount:
         def __init__(self, name, balance):
             self._name = name
             self._balance = balance
             self._transaction_fee = 5.00
         def deposit(self, amount):
            if (self._balance + amount) < 0:
                raise Exception("Balance cannot go below 0.")
            else:
                self._balance = self._balance + amount
         def withdraw(self, amount):
            if (self._balance - amount) < 0:
                raise Exception("Balance cannot go below 0.")
            else:
                self._balance = self._balance - amount
    

    在现实生活中,您会创建自己的 Exception 子类并引发它。

    【讨论】:

      猜你喜欢
      • 2019-01-14
      • 1970-01-01
      • 2015-06-24
      • 1970-01-01
      • 2016-11-03
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2018-02-08
      相关资源
      最近更新 更多