4

I need to read an input file (input.txt) which contains one line of integers (13 34 14 53 56 76) and then compute the sum of the squares of each number.

This is my code:

# define main program function
def main():
    print("\nThis is the last function: sum_of_squares")
    print("Please include the path if the input file is not in the root directory")
    fname = input("Please enter a filename : ")
    sum_of_squares(fname)

def sum_of_squares(fname):
    infile = open(fname, 'r')
    sum2 = 0
    for items in infile.readlines():
        items = int(items)
        sum2 += items**2
    print("The sum of the squares is:", sum2)
    infile.close()

# execute main program function
main()

If each number is on its own line, it works fine.

But, I can't figure out how to do it when all the numbers are on one line separated by a space. In that case, I receive the error: ValueError: invalid literal for int() with base 10: '13 34 14 53 56 76'

Yannis
  • 1,682
  • 7
  • 27
  • 45
Shawn Coward
  • 43
  • 1
  • 4

4 Answers4

5

You can use file.read() to get a string and then use str.split to split by whitespace.

You'll need to convert each number from a string to an int first and then use the built in sum function to calculate the sum.

As an aside, you should use the with statement to open and close your file for you:

def sum_of_squares(fname):

    with open(fname, 'r') as myFile: # This closes the file for you when you are done
        contents = myFile.read()

    sumOfSquares = sum(int(i)**2 for i in contents.split())
    print("The sum of the squares is: ", sumOfSquares)

Output:

The sum of the squares is: 13242
Farhan.K
  • 3,425
  • 2
  • 15
  • 26
2

You are trying to turn a string with spaces in it, into an integer.

What you want to do is use the split method (here, it would be items.split(' '), that will return a list of strings, containing numbers, without any space this time. You will then iterate through this list, convert each element to an int as you are already trying to do.

I believe you will find what to do next. :)


Here is a short code example, with more pythonic methods to achieve what you are trying to do.

# The `with` statement is the proper way to open a file.
# It opens the file, and closes it accordingly when you leave it.
with open('foo.txt', 'r') as file:
    # You can directly iterate your lines through the file.
    for line in file:
        # You want a new sum number for each line.
        sum_2 = 0
        # Creating your list of numbers from your string.
        lineNumbers = line.split(' ')
        for number in lineNumbers:
            # Casting EACH number that is still a string to an integer...
            sum_2 += int(number) ** 2
        print 'For this line, the sum of the squares is {}.'.format(sum_2)
IMCoins
  • 3,149
  • 1
  • 10
  • 25
2

You could try splitting your items on space using the split() function.

From the doc: For example, ' 1 2 3 '.split() returns ['1', '2', '3'].

def sum_of_squares(fname):
    infile = open(fname, 'r')
    sum2 = 0
    for items in infile.readlines():
        sum2 = sum(int(i)**2 for i in items.split())
    print("The sum of the squares is:", sum2)
    infile.close()
Halee
  • 492
  • 9
  • 15
  • 1
    Right... but if you try this - you'll get an error because `items = int(items.split())` is a list and you won't be able to convert that to an `int` - you want to loop over that list and convert each item and then add... – Jon Clements Dec 18 '17 at 16:19
  • Thanks, good catch @JonClements. It looks like Farhan.K has updated his answer to cover this case now. – Halee Dec 18 '17 at 16:37
  • I still don't believe he has the knowledge to understand this one-liner expression if he has problems differentiating lists, from strings, from integers, etc.. – IMCoins Dec 18 '17 at 16:41
0

Just keep it really simple, no need for anything complicated. Here is a commented step by step solution:

def sum_of_squares(filename):

    # create a summing variable
    sum_squares = 0

    # open file
    with open(filename) as file:

        # loop over each line in file
        for line in file.readlines():

            # create a list of strings splitted by whitespace
            numbers = line.split()

            # loop over potential numbers
            for number in numbers:

                # check if string is a number
                if number.isdigit():

                    # add square to accumulated sum
                    sum_squares += int(number) ** 2

    # when we reach here, we're done, and exit the function
    return sum_squares

print("The sum of the squares is:", sum_of_squares("numbers.txt"))

Which outputs:

The sum of the squares is: 13242
RoadRunner
  • 25,803
  • 6
  • 42
  • 75