内部检查系统错误-传递命令行参数

问题描述

您好,我在HyperSkill从事信用计算器项目时,在检查信用计算器最后阶段的代码结果时,当我尝试对其进行检查时出现“内部系统检查错误”。该代码正在我的IDE(pycharm)上运行,但是不知何故出现了“内部系统检查错误”。您能帮忙弄清楚吗?

项目说明: 在此阶段,您需要实现以下功能

计算差异付款。为此,用户可以运行指定利息,期间数和信用本金的程序。 能够计算与上一阶段的年金支付相同的值(本金,周期数和支付值)。用户使用命令行参数指定所有已知参数,因此将有一个未知参数。这是用户要计算的值。 处理无效的参数。如果参数无效,则显示错误消息“参数不正确”是个好主意。 程序的最终版本应该可以从命令行运行,并解析以下参数:

  • -type,指示付款类型:“年金”或“差异”(区分)。如果--type既未指定为“ annuity”也未指定为“ diff”,或者根本未指定,则显示错误消息。

python creditcalc.py --principal = 1000000 --periods = 60 --interest = 10 参数不正确

  • -付款,指每月付款。对于--type = diff,每个月的付款都不同,因此我们无法计算期数或本金,因此,它与--payment的组合也无效:

python creditcalc.py --type = diff --principal = 1000000 --interest = 10 --payment = 100000 参数不正确

  • -本金用于计算两种付款方式。知道利息,年金支付和期数,就可以得到其价值。
  • -periods参数表示还款所需的月数和/或年数。它是根据利息,年金支付和本金计算的。
  • -指定利息时不带百分号。请注意,它可以接受浮点值。我们的信用计算器无法计算利息,因此这些参数不正确:

python creditcalc.py --type =年金-本金= 100000-付款= 10400-期限= 8 参数不正确

我的代码

# Stage 4/4 of the credit calculator project
import sys
import math

args = sys.argv

if len(sys.argv) == 5:
    type1 = sys.argv[1].split('=')[1]
    credit_principal = int(sys.argv[2].split('=')[1])
    periods = int(sys.argv[3].split('=')[1])
    credit_interest = float(sys.argv[4].split('=')[1])
    nominal_interest = credit_interest / (12 * 100)

    if type1 == 'diff' or type1 == 'annuity' and credit_principal > 0 \
            and credit_interest > 0 and periods > 0:

        if type1 == "diff":

            sum_diff_payments = 0
            for i in range(1,periods + 1):
                montly_diff_payment = math.ceil(credit_principal / periods + nominal_interest * (
                        credit_principal - credit_principal * (i - 1) / periods))
                sum_diff_payments += montly_diff_payment
                print(f"Month {i}: payment is {montly_diff_payment}")
            print("\nOverpayment =",int(sum_diff_payments - credit_principal))

        else:
            if sys.argv[2].split('=')[0] == '--principal' and sys.argv[3].split('=')[0] == '--periods':

                annuity = math.ceil(credit_principal * (nominal_interest * math.pow(1 + nominal_interest,periods) / (
                        math.pow(1 + nominal_interest,periods) - 1)))
                print(f"Your annuity payment =  {annuity}!")
                print("Overpayment =",int(annuity * periods - credit_principal))

            elif sys.argv[2].split('=')[0] == '--payment' and sys.argv[3].split('=')[0] == '--periods':

                annuity = int(sys.argv[2].split('=')[1])
                credit = math.floor(annuity / ((nominal_interest * math.pow(1 + nominal_interest,periods)) / (
                            math.pow(1 + nominal_interest,periods) - 1)))
                print(f"Your credit principal = {credit}!")
                print("Overpayment = ",annuity * periods - credit)
                #Your credit principal = 800018!
                #Overpayment = 246622

            else:

                payment = int(sys.argv[3].split('=')[1])

                months = math.ceil(math.log(payment / (payment - nominal_interest * credit_principal),1 + nominal_interest))
                years = months // 12
                months = months % 12
                if months != 0:
                    print(f"You need {years} years and {months} months to repay this credit!")
                else:
                    print(f"You need {years} ","years" if years > 1 else "year","to repay this credit!")

                print("Overpayment =",int(payment * (years * 12 + months) - credit_principal))

    else:
        print("Incorrect parameters")
        sys.exit()

else:
    print("Incorrect parameters")
    sys.exit()

解决方法

我合理的解释是它的发生是由于一个无限循环,最有可能是等待解析系统参数向量的错误。这里也提到了同样的问题(Credit Calculator Stage 4 - Internal System Check Error),没有提出解决方案。

与其通过cmd行解析输入,不如尝试使用argparse之类的模块并预先设置输入的值。

这里是一个上下文无关的示例,显示了其用法

import argparse
    
# check command line options
parser = argparse.ArgumentParser()

parser.add_argument("--type",dest="type_of_payment",type=str,choices=["diff","annuity"],required=True,help="Add some help text here")
parser.add_argument("--periods",dest="period_count",type=int,required=True)
parser.add_argument("--payment",dest="monthly_payment",type=float,required=True)
parser.add_argument("--interest",dest="credit_interest",required=True)
parser.add_argument("--principal",dest="credit_principal",required=True)

args = parser.parse_args()

# show the values
print(f"Type of payment: {args.type_of_payment}")
print(f"Periods: {args.period_count}")
print(f"Payment: {args.monthly_payment}")
print(f"Interest: {args.credit_interest}")
print(f"Principal: {args.credit_principal}")
,

最后,我找出了问题和解决方案!如HyperSkill中的项目示例所示-正确的参数可以是5,并且可以是不同的元素。示例:

> python creditcalc.py --type=annuity --principal=1000000 --periods=60 --interest=10

> python creditcalc.py --type=annuity --payment=8722 --periods=120 --interest=5.6

是正确的输入,请注意元素的差异。在第一个中没有付款参数,在第二个中有主体参数。因此,根据输入args的类型,参数的顺序将不同,但长度相同。

首先,需要使用argparser声明所有参数并设置required = False

parser = argparse.ArgumentParser()
parser.add_argument("--type",required=False)
parser.add_argument("--principal",required=False)
parser.add_argument("--periods",required=False)
parser.add_argument("--payment",required=False)
parser.add_argument("--interest",required=False)

读取变量的参数:

args,leftovers = parser.parse_known_args()

然后找出传递了哪些参数-您需要计算

> python creditcalc.py --type=annuity --payment=8722 --periods=120 --interest=5.6

> python creditcalc.py --type=diff --principal=1000000 --payment=104000

> python creditcalc.py --type=annuity --principal=500000 --payment=23000 --interest=7.8

您可以使用以下简单的if语句进行检查:

if args.type is not None and args.principal is not None and args.periods is not None and args.interest is not None:
pass
elif args.type is not None and args.payment is not None and args.periods is not None and args.interest is not None:
pass