Python Forum
Thread Rating:
  • 0 Vote(s) - 0 Average
  • 1
  • 2
  • 3
  • 4
  • 5
sum of lisit with no inputs
#1
Hi.

Creating a program which is working fine-ish.
Big bug I can't get around is that as part of program are two empty lists which have numbers put into them coming from user inputs.
Lists are then summed and these sums are put into two variables to be used as part of a final calculation. All works fine.
But sometimes there are no inputs on either or both of them.
When the program does the final calculation, an error occurs -

NameError: name 'cis_total_1' is not defined

Which makes sense, as there is nothing to sum. So I tried starting each list with 0 in it. Same error. Which doesn't make sense unless the sum of zero, being zero, isn't valid. Any ideas?

Or ignore empty list at time of final calculation. And how to ignore an empty list?
Reply
#2
please show the code
Reply
#3
Code is below.

So you don't have to trawl through the whole lot:
The lists are at lines 49 and 50.
The first list is appended at line 59
The second list is appended at line 89
The first list is summed at line 134
The second list is summed at line 152
The final calculation involving both summed lists is at line 104


Thank you.




import openpyxl
from openpyxl import load_workbook
from openpyxl.styles import Font
import os
import sys
import datetime
from shutil import copyfile
import time


wb = load_workbook(r'C:\Users\Ron McMillan\OneDrive\CIS Monthly report\Returns 2018-19\CIS monthly.xlsx')
sh = wb['CIS']


sh.delete_rows(1,50)


def tax_month_number():
    tax_month_tuple = (10,11,12,1,2,3,4,5,6,7,8,9)
    month_number = today.month - 1
    tax_month = tax_month_tuple [(month_number)]
    sh['F5'] = ('Tax month ' + str(tax_month))


today = datetime.date.today()
print(today)
sh['A5'] = ("CIS Return")
sh['B5'] = ("Until 5th " + str(today.strftime("%B")) + " " + str(today.year))

img = openpyxl.drawing.image.Image(r'RMES_head_sliced.png')
img.anchor = 'A1'
img.width = 175
img.height = 75
sh.add_image(img)

sh['A8'] = "Date"
sh['B8'] = "Contractor"
sh['C8'] = 'UTR'
sh['D8'] = 'Labour'
sh['E8'] = 'Materials'
sh['F8'] = 'VAT'
sh['G8'] = "Total"
sh['H8'] = "CIS"


global cis_add_list
global rmes_cis_add_list

rmes_cis_add_list = [0]
cis_add_list = [0]

def contractor_deets():
    contractor = input("Contractor:\n")
    date_paid = input("Date paid:\n")
    utr = int(input("UTR:\n"))
    labour = float(input("Labour:\n"))
    materials = float(input("Material:\n"))
    cis_deducted = float(labour) * 0.2
    cis_add_list.append(cis_deducted)

    vat = input('VAT? Y/N  ').upper()
    if vat == 'Y':
        net_total = float(labour) + float(materials)
        vat_total = float(net_total) * 0.2
        gross = net_total + vat_total
    elif vat == 'N':
        vat_total = 0.00
        net_total = float(labour) + float(materials)
        gross = net_total

    input_row = sh.max_row + 1
    sh['A{}'.format(input_row)] = date_paid
    sh['B{}'.format(input_row)] = contractor
    sh['C{}'.format(input_row)] = utr
    sh['D{}'.format(input_row)] = labour
    sh['E{}'.format(input_row)] = vat_total
    sh['F{}'.format(input_row)] = materials
    sh['G{}'.format(input_row)] = gross
    sh['H{}'.format(input_row)] = cis_deducted

def rmes_cis_deductions():
    main_contractor = input("Main Contractor:\n")
    date_invoice_paid = input("Date paid:\n")
    rmes_invoice = input("RMES invoice number:\n")
    rmes_labour = float(input("Labour:\n"))
    rmes_materials = float(input("Material:\n"))
    rmes_net = float(rmes_labour) + float(rmes_materials)
    rmes_cis_deducted = float(rmes_labour) * 0.2
    rmes_cis_add_list.append(rmes_cis_deducted)

    input_row = sh.max_row + 1
    sh['A{}'.format(input_row)] = date_invoice_paid
    sh['B{}'.format(input_row)] = main_contractor
    sh['C{}'.format(input_row)] = rmes_invoice
    sh['D{}'.format(input_row)] = rmes_labour
    sh['E{}'.format(input_row)] = rmes_materials
    sh['F{}'.format(input_row)] = rmes_net
    sh['G{}'.format(input_row)] = rmes_cis_deducted


def hmrc():
    hmrc_payment = float(input('Payment to HMRC:\n '))
    hmrc_credit = float(input('Credit with HMRC:\n '))
    hmrc_due = float(hmrc_payment)+float(hmrc_credit)+float(cis_total_1 - cis_total_2)
    sh['A30'] = 'HMRC payment'
    sh['C30'] = hmrc_payment
    sh['A31'] = 'Credit with HMRC'
    sh['C31'] = hmrc_credit
    sh['A32'] = 'Total due to HMRC'
    sh['C32'] = hmrc_due

def end_off():
    print('end of')
    wb.save(r'C:\Users\Ron McMillan\OneDrive\CIS Monthly report\Returns 2018-19\CIS monthly.xlsx')
    wb.close()
    time.sleep(2)
    src_path = r'C:\Users\Ron McMillan\OneDrive\CIS Monthly report\Returns 2018-19'
    src_file = os.path.join(src_path, 'CIS monthly.xlsx')
    dest_file = os.path.join(src_path, f'CIS_Month_Till_5th_{str(today.strftime("%b"))}_{today.year}.xlsx')
    copyfile(src_file, dest_file)
    #os.startfile(dest_file, 'print')
    time.sleep(2)
    os.startfile(dest_file)

tax_month_number()

new_contractor_payment = input('New entry? Y/N ').upper()
while new_contractor_payment == 'Y':
    contractor_deets()
    new_contractor_payment = input('New entry? Y/N ').upper()
    if new_contractor_payment != 'Y':

        sh['G16'] = 'Total CIS '
        cis_total_1 = sum(cis_add_list)
        sh['H16'] = cis_total_1
        break

sh['A18'] = "Date paid"
sh['B18'] = "Contractor"
sh['C18'] = 'Invoice #'
sh['D18'] = 'Labour'
sh['E18'] = 'Materials'
sh['F18'] = " Net Total"
sh['G18'] = "CIS deducted"

rmes_new_cis_deduct = input('Suffered CIS deduction? Y/N ').upper()
while rmes_new_cis_deduct == 'Y':
    rmes_cis_deductions()
    new_cis_deduct = input('New CIS deduction? Y/N ').upper()
    if new_cis_deduct != 'Y':
        sh['G26'] =  'Total CIS deduct'
        cis_total_2 = sum(rmes_cis_add_list)
        sh['H26'] = cis_total_2
        break
hmrc()

end_off()

time.sleep(2)

sys.exit()
Reply
#4
Nothing jumps out at me, and I can't run you code as I don't have access to the data.
Would you please post the entire unmodified error traceback (in error tags). Sorry I didn't request last post, but in the future, always post the full error traceback as there's some very valuable information within.
Reply
#5
Hi.

Traceback as follows

Error:
Traceback (most recent call last): File "C:/Users/Ron McMillan/PycharmProject/invoice_generator/monthly_cis.py", line 155, in <module> hmrc() File "C:/Users/Ron McMillan/PycharmProject/invoice_generator/monthly_cis.py", line 104, in hmrc hmrc_due = float(hmrc_payment)+float(hmrc_credit)+float(cis_total_1 - cis_total_2) NameError: name 'cis_total_1' is not defined
Process finished with exit code 1


Ran with nothing in lists at the beginning. But same error even if lists start with a (0) in them.

Thank you
Reply
#6
That variable doesn't exist in the scope of the hmrc function. Why would you expect to be able to use it there? You should pass the values into your functions as arguments, rather than relying on them being globally available.
Reply
#7
ok, ok, processing - still getting my head around programming.
What you say makes sense.
But it works when there are inputs. I guess because they are global.
Thank you. Have a direction now.
Reply
#8
The error is spot on. There is no object named cis_total_1,
nor is cis_total_2 are you trying to access the list ? which would be done (for example with cis_add_list)
like:
cis_add_list[0] # first element (or cell)
cis_add_list[1] # second element (or cell)
cis_add_list[2] # third element (or cell)
...
Reply
#9
What throws me is that it works as long as I add something to each list.
But if I add nothing to the list it doesn't work.
Still trying to get my head around the answers given - they may be correct but I don't know what to do with the info.

I will create a completely stripped down version of the program so the problem is clear - to me as well as anyone else.

This is the relevant code without everything else, and with extra print statements so I can follow the inputs and calculations.

global cis_add_list
global rmes_cis_add_list

rmes_cis_add_list = [0]
cis_add_list = [0]

def contractor_deets():
    labour = float(input("Labour:\n"))
    cis_deducted = float(labour) * 0.2
    cis_add_list.append(cis_deducted)
    print(cis_add_list)

def rmes_cis_deductions():
    rmes_labour = float(input("Labour:\n"))
    rmes_cis_deducted = float(rmes_labour) * 0.2
    rmes_cis_add_list.append(rmes_cis_deducted)
    print(rmes_cis_add_list)

def hmrc():
    hmrc_payment = float(input('Payment to HMRC:\n '))
    hmrc_credit = float(input('Credit with HMRC:\n '))
    hmrc_due = float(hmrc_payment)+float(hmrc_credit)+float(cis_total_1 - cis_total_2)
    print(hmrc_due)


new_contractor_payment = input('New entry? Y/N ').upper()
while new_contractor_payment == 'Y':
    contractor_deets()
    new_contractor_payment = input('New entry? Y/N ').upper()
    if new_contractor_payment != 'Y':
        cis_total_1 = sum(cis_add_list)
        print(cis_total_1)
        break

rmes_new_cis_deduct = input('Suffered CIS deduction? Y/N ').upper()
while rmes_new_cis_deduct == 'Y':
    rmes_cis_deductions()
    new_cis_deduct = input('New CIS deduction? Y/N ').upper()
    if new_cis_deduct != 'Y':
        cis_total_2 = sum(rmes_cis_add_list)
        print(cis_total_2)
        break
hmrc()
Works fine as long as there is at least one input each for the first two functions.

If you don't have any inputs then then:

NameError: name 'cis_total_1' is not defined.

So, bear with me if I am missing something obvious (maybe some nomenclature?)

1. Is cis_total_1 not defined because there is nothing in the list to sum?
2. Following on from what ndc8530 said about passing in the variables to the function as arguments gives me this in my mind:

def hmrc(cis_total_1,cis_total_2):
    hmrc_payment = float(input('Payment to HMRC:\n '))
    hmrc_credit = float(input('Credit with HMRC:\n '))
    hmrc_due = float(hmrc_payment)+float(hmrc_credit)+float(cis_total_1 - cis_total_2)
    print(hmrc_due)
but something is missing, not correct or I have the wrong end of the stick.

Pointers?

Thanks in advance.

Ok. So if I change the code to have the variables as arguments like this:

rmes_cis_add_list = []
cis_add_list = []

def contractor_deets():
    labour = float(input("Labour:\n"))
    cis_deducted = float(labour) * 0.2
    cis_add_list.append(cis_deducted)
    print(cis_add_list)

def rmes_cis_deductions():
    rmes_labour = float(input("Labour:\n"))
    rmes_cis_deducted = float(rmes_labour) * 0.2
    rmes_cis_add_list.append(rmes_cis_deducted)
    print(rmes_cis_add_list)

def hmrc(cis_total_1,cis_total_2):
    hmrc_payment = float(input('Payment to HMRC:\n '))
    hmrc_credit = float(input('Credit with HMRC:\n '))
    hmrc_due = float(hmrc_payment)+float(hmrc_credit)+float(cis_total_1 - cis_total_2)
    print(hmrc_due)


new_contractor_payment = input('New entry? Y/N ').upper()
while new_contractor_payment == 'Y':
    contractor_deets()
    new_contractor_payment = input('New entry? Y/N ').upper()
    if new_contractor_payment != 'Y':
        cis_total_1 = sum(cis_add_list)
        print(cis_total_1)
        break

rmes_new_cis_deduct = input('Suffered CIS deduction? Y/N ').upper()
while rmes_new_cis_deduct == 'Y':
    rmes_cis_deductions()
    new_cis_deduct = input('New CIS deduction? Y/N ').upper()
    if new_cis_deduct != 'Y':
        cis_total_2 = sum(rmes_cis_add_list)
        print(cis_total_2)
        break
hmrc(cis_total_1,cis_total_2)
It does the same as the previous version without making the lists global.

Progress.

But, if there is no input to the list, then still-


NameError: name 'cis_total_1' is not defined.

So how would I get around a zero sum list? Some if statement in the hmrc function. Kinda thinking aloud here.
Reply
#10
NameError: name 'cis_total_1' is not defined.

You can't get into the green car if there is no green car!

Please search your code. You will not find the variable cis_total_1
Reply


Forum Jump:

User Panel Messages

Announcements
Announcement #1 8/1/2020
Announcement #2 8/2/2020
Announcement #3 8/6/2020