I am trying to use the transfer_to_saving
method in the CheckingAccount
class. However, whenever I create a SavingAccount
object, the self.has_saving = True
does not change the class attribute to True
. So, whenever I try to transfer funds, it prints Must create a saving account
.
class CheckingAccount(Account):
balance = 0
def __init__(self, account_number, pin):
super().__init__(account_number)
self.SavingAccount = SavingAccount
self.pin = pin
def deposit(self, amount):
old_bal = self.balance
self.balance += amount
print(f'Previous Balance: ${old_bal}\nDeposit amount: ${amount}\nNew Balance: ${self.balance}')
def withdraw(self, pin, amount):
if pin == self.pin:
self.balance -= print('Insufficient funds') if amount > self.balance else amount
else:
print('Invalid PIN')
def transfer_to_saving(self, amount):
if self.SavingAccount.has_saving is False:
print('Must create a saving account')
elif amount > self.balance:
print('Insufficient funds')
else:
self.SavingAccount.balance += amount
self.balance -= amount
class SavingAccount(Account):
balance = 0
has_saving = False
def __init__(self, account_number):
super().__init__(account_number)
self.CheckingAccount = CheckingAccount
self.has_saving = True
def deposit(self, amount):
self.balance += amount
Am I doing this right? Shouldn't the init
method be changing the class attribute?
---UPDATE---
The goal I am trying to accomplish is to find out whether the user has already created a saving account. I have additional User classes that I did not include since it would be a bit overkill. However, the goal is to prevent a user from transferring money from checking to saving if they don't have a saving account.
You are not actually creating an instance of SavingAccount
with this line:
self.SavingAccount = SavingAccount
You are assigning the self.SavingAccount
attribute to the SavingAccount
class defined below.
You need to call the SavingAccount
constructor, like this:
self.saving_account = SavingAccount(account_number)
Note that the Python convention is to use lower_snake_case
for attributes/variables, and UpperCamelCase
for class names.
You are doing the same thing on this line in the SavingAccount
constructor:
self.CheckingAccount = CheckingAccount
I'm not sure what the goal is here, but if you want every SavingAccount
to hold a reference to a CheckingAccount
and vice versa, it might be cleaner to do it like this:
class CheckingAccount(Account):
def __init__(self, account_number, pin):
super().__init__(account_number)
self.saving_account = SavingAccount(account_number, self)
self.pin = pin
class SavingAccount(Account):
def __init__(self, account_number, checking_account):
super().__init__(account_number)
self.checking_account = checking_account
With this, whenever you create a CheckingAccount
you will get a corresponding SavingAccount
and they will each hold a reference to each other. I think it's still a bit weird conceptually, since the account numbers would be the same, so it might be better to just create them separately like this:
class CheckingAccount(Account):
def __init__(self, account_number, pin):
super().__init__(account_number)
self.saving_account = None # to be assigned later
self.pin = pin
class SavingAccount(Account):
def __init__(self, account_number):
super().__init__(account_number)
self.checking_account = None # to be assigned later
checking_account_number = 123
checking = CheckingAccount(checking_account_number)
saving_account_number = 456
saving = SavingAccount(saving_account_number)
checking.saving_account = saving
saving.checking_account = checking
Finally, the has_saving
attribute of SavingAccount
is not necessary at all. A cleaner way to check if a SavingAccount
is to use isinstance
:
def transfer_to_saving(self, amount):
if not isinstance(self.saving_account, SavingAccount):
print('Must create a saving account')
elif amount > self.balance:
print('Insufficient funds')
else:
self.saving_account.balance += amount
self.balance -= amount