问题是编写计算贷款利息的python并打印付款计划。贷款的利息可以根据简单的公式计算:
I = P×R×T
我是支付的利息,P是借入的金额(本金),R是利率,T是贷款的长度。
最后需要显示如下:
该计划将打印借入的金额,支付的利息总额,每月付款金额以及付款时间表。
示例会话
Loan calculator
Amount borrowed: 100
Interest rate: 6
Term (years): 1
Amount borrowed: $100.00
Total interest paid: $6.00
Amount Remaining
Pymt# Paid Balance
----- ------- ---------
0 $ 0.00 $106.00
1 $ 8.84 $ 97.16
2 $ 8.84 $ 88.32
3 $ 8.84 $ 79.48
4 $ 8.84 $ 70.64
5 $ 8.84 $ 61.80
6 $ 8.84 $ 52.96
7 $ 8.84 $ 44.12
8 $ 8.84 $ 35.28
9 $ 8.84 $ 26.44
10 $ 8.84 $ 17.60
11 $ 8.84 $ 8.76
12 $ 8.76 $ 0.00
完整的问题描述如下:http://openbookproject.net/pybiblio/practice/wilson/loan.php 为此,我编写了如下代码:
import decimal
from decimal import *
class loan_calc:
def __init__(self):
decimal.getcontext().prec = 3
p = Decimal(input('Please enter your loan amount:'))
r = Decimal(input('Please enter the rate of interest:'))
t = Decimal(input('Please enter loan period:'))
r_e = r/100
i = p*r_e*t
term = t*12
r_a = p+i
amnt = p/term
count = 0
b_r = r_a
print "Payment\t\tAmount Paid\t\tBal.Rem."
while count <= term:
if count == 0:
print count,"\t\t"'0.00'"\t\t\t",b_r
count += 1
b_r -= amnt
continue
if term - count == 1:
amnt = b_r
print count,"\t\t",amnt,"\t\t\t",b_r
count += 1
b_r -= amnt
continue
else:
print count,"\t\t",amnt,"\t\t\t",b_r
b_r -= amnt
count += 1
continue
loan = loan_calc()
答案 0 :(得分:2)
使用Decimal(input())
是错误的:
>>> decimal.getcontext().prec=3
>>> decimal.Decimal(input('enter the number: '))
enter the number: 0.1
Decimal('0.1000000000000000055511151231257827021181583404541015625')
使用input
会导致Python评估输入,从而创建浮点值。使用raw_input
并将字符串直接传递给Decimal
:
>>> decimal.Decimal(raw_input('enter the number: '))
enter the number: 0.1
Decimal('0.1')
将代码缩进4个空格,跟随PEP 8,并避免使用单字符变量名。
答案 1 :(得分:2)
首先,我建议不要同时执行import decimal
和from decimal import *
。选择一个并从那里使用你需要的东西。通常,我会import whatever
然后使用whatever.what_is_needed
来保持名称空间更清晰。
评论者已经注意到,没有必要为这么简单的事情创建课程(除非这是家庭作业而你的导师需要它)。删除类声明,将def __init__(self)
更改为def main()
,并调用main当前实例化loan_class的位置。有关主要功能的更多信息,请参阅Guido's classic post有关它们的信息。
应检查输入值。一个简单的方法是使用try-except块,因为它们被转换为Decimal。代码看起来像:
prin_str = raw_input('Please enter your loan amount: ')
try:
principal = decimal.Decimal(prin_str)
except decimal.InvalidOperation:
print "Encountered error parsing the loan amount you entered."
sys.exit(42)
要使其工作,您必须在sys.exit()调用之前的某个时间import sys
。我通常把我的导入放在文件的开头。
由于您的所有输入都属于同一类型,因此您可以轻松地将其作为常规使用函数,然后为每个输入调用该函数。
计算中似乎存在某种错误。解决这个问题留给读者练习。 ; - )
答案 2 :(得分:1)
重写(在Python 3中,抱歉)。我不确定我理解算法,但你可以修改它。也许这会有所帮助吗?
import decimal
balance = decimal.Decimal(input("Amount borrowed: "))
rate = decimal.Decimal(input("Rate (%): ")) / 100
term = int(input("Term (years): "))
print("\t".join(s.rjust(15) for s in ("Payment", "Amount Paid", "Balance")))
print("-"*54)
balance *= (1 + rate * term)
payment = balance / (12 * term)
total = 0
for month in range(12 * term):
if balance < payment:
payment = balance
print(("{: >15.2f}\t"*3)[:-1].format(payment, total, balance))
total += payment
balance -= payment
请注意以下事项:
while
循环多个案例。您将在该术语中每月打印一行,因此请使用for
循环。答案 3 :(得分:1)
这是一个与你的写作方式密切相关的答案。使用我在询问how to round off a floating number in python时解释和建议的方法,它使用与decimal
模块的math
函数等效的ceil
模块来获得相同的答案,如下所示。练习链接(除了一些小的输出格式)。我还将代码重新缩进到更常用的4空格,并将变量重命名为更具可读性。希望你从中学到一些东西。请注意,我不将decimal.getcontext().prec
设置为3
(我不相信它符合您的想法)。
import decimal
def main():
principle = decimal.Decimal(raw_input('Please enter your loan amount:'))
rate = decimal.Decimal(raw_input('Please enter rate of interest (percent):')) / 100
term = decimal.Decimal(raw_input('Please enter loan period (years):')) * 12
interest = (principle * rate).quantize(decimal.Decimal('.01'), rounding=decimal.ROUND_HALF_EVEN)
balance = principle + interest
payment = (balance / term).quantize(decimal.Decimal('.01'), rounding=decimal.ROUND_CEILING)
print "Payment\t\tAmount Paid\t\tRem.Bal."
for count in range(1+term):
if count == 0:
print count, "\t\t0.00\t\t\t", balance
elif count == term: # last payment?
payment = balance
balance -= payment
print count, "\t\t", payment, "\t\t\t", balance
else:
balance -= payment
print count, "\t\t", payment, "\t\t\t", balance
main()
# > python loan_calc.py
# Please enter your loan amount:100
# Please enter rate of interest (percent):6
# Please enter loan period (years):1
# Payment Amount Paid Rem.Bal.
# 0 0.00 106.00
# 1 8.84 97.16
# 2 8.84 88.32
# 3 8.84 79.48
# 4 8.84 70.64
# 5 8.84 61.80
# 6 8.84 52.96
# 7 8.84 44.12
# 8 8.84 35.28
# 9 8.84 26.44
# 10 8.84 17.60
# 11 8.84 8.76
# 12 8.76 0.00
答案 4 :(得分:1)
逻辑与之前的答案大致相同,但严重重新格式化。享受!
# Loan payment calculator
import decimal
def dollarAmt(amt):
"Accept a decimal value and return it rounded to dollars and cents"
# Thanks to @Martineau!
# I found I had to use ROUND_UP to keep the final payment
# from exceeding the standard monthly payments.
return amt.quantize(decimal.Decimal('0.01'), rounding=decimal.ROUND_UP)
def getAmt(msg):
"Get user input and return a decimal value"
return decimal.Decimal(raw_input(msg))
class MonthlyFixedPaymentLoan(object):
def __init__(self, principal, yearlyRate, months):
self.principal = principal
self.yearlyRate = yearlyRate
self.months = months
self.interest = dollarAmt(principal * yearlyRate * (months/12))
self.balance = principal + self.interest
self.payment = dollarAmt(self.balance / months)
def __str__(self):
return ("Amount borrowed: ${0:>10}\n" +
"Total interest paid: ${1:>10}").format(dollarAmt(self.principal), dollarAmt(self.interest))
def payments(self):
# 'month 0'
yield 0, decimal.Decimal('0.00'), self.balance
pmt = self.payment
bal = self.balance
for mo in range(1,self.months):
bal -= pmt
yield mo, pmt, bal
# final payment
yield self.months, bal, decimal.Decimal('0.00')
def main():
amt = getAmt('Amount borrowed ($): ')
rate = getAmt('Interest rate (%/yr): ')
pd = getAmt('Loan term (years): ')
loan = MonthlyFixedPaymentLoan(amt, rate/100, pd*12)
print('')
print(loan)
print('')
print('Month Payment Balance')
print('----- -------- ----------')
for mo,pay,rem in loan.payments():
print('{0:>4} ${1:>7} ${2:>9}'.format(mo, pay, rem))
if __name__=="__main__":
main()