0

EDIT: Thank you for the responses, which are helpful, but I'm not sure they're getting at the core of my problem. In some cases it would be nice to simply select the lower of the lists and then add the values accordingly, but in THIS case I actually want to treat uneven lists as though the shorter list had zero values for the values it was missing. So I want [1, 2, 3] + [1, 2] to function as [1, 2, 3] + [1, 2, 0]. I don't think zip, or reversing my operator, will accomplish this.

I'm trying to create a function that adds the corresponding values of two lists and returns a new list with the sums of each of the indices of the two original lists:

def addVectors(v1, v2):
    print(v1[0], v1[1], v2[0])
    newVector = []
    if len(v1) > len(v2):
        for index in range(len(v1)):
            print(index)
            newVector[index] += v1[index] + v2[index]
    else:
        for index in range(len(v2)):
            print(index)
            newVector[index] += v2[index] + v1[index]
    return newVector


addVectors([1, 2, 3], [1, 2])

Yet I'm getting an error stating that the list index is out of range? Not sure what I'm doing wrong in this seemingly simple program....

8
  • 4
    What should be done with the 3 value? Your lists are of unequal length, so 3 has no corresponding value. Commented Sep 20, 2012 at 21:10
  • Right, that is one problem . . . is there an equivalent to the .get method for dictionaries, where I can specify an index to look for but give a default value if it is undefined? Or will I have to use more conditional logic? But my program is crashing before it even gets to that point. It prints "index" once, then it says the assignment index is out of range at some point when it is doing the newVector[index] = v1[index] + v2[index] code. Commented Sep 20, 2012 at 21:13
  • See also this question for the general case (more than two lists) Commented Sep 20, 2012 at 21:14
  • @user1427661 It's generally more advisable to raise an error if you're given two lists of unequal length. This usually indicates a logic error before your function was even called, and the programmer would probably like to know this instead of your function ignoring the potential problem. Commented Sep 20, 2012 at 21:16
  • @cdhowie: Not necessarily. For example, if zip is given two lists of unequal length, it goes to the shorter one. Commented Sep 20, 2012 at 21:18

7 Answers 7

7

You probably meant to change the line:

if len(v1) > len(v2):

to:

if len(v1) < len(v2):

That way, you are iterating to the number of elements in v1 when v1 is shorter, which prevents you from going over the edge.

Note that this would also throw an error because newVector is a list of length 0 and you are accessing outside of its range. You'd have to change

newVector[index] += v1[index] + v2[index]

to

newVector.append(v1[index] + v2[index])

However, note that this can be done much more simply as:

def addVectors(v1, v2):
    return map(sum, zip(v1, v2))

ETA: To pad the list with zeros, do:

import itertools
def addVectors(v1, v2):
    return map(sum, itertools.izip_longest(v1, v2, fillvalue=0))

For example:

addVectors([1, 2, 3, 4, 5], [1, 2])
# [2, 4, 3, 4, 5]
Sign up to request clarification or add additional context in comments.

Comments

4

Why not just use this?

def sum_lists(a, b):
    return [x[0] + x[1] for x in zip(a, b)]

sum_lists([1, 2, 3], [4, 5, 6])    # -> [5, 7, 9]

Comments

2

You compare the lengths of the list, which is correct. But then you change the required operations. I.e. when list1 is longer than list2, you should only loop over the elements for the length of list2.

Comments

2

To fill the lists of uneven length, you can use itertools:

>>> import itertools
>>> map(sum, itertools.izip_longest([1,2,3], [1,2], fillvalue = 0))
[2, 4, 3]

Comments

1

Your problem lies here:

if len(v1) > len(v2):
    for index in range(len(v1)):
        print(index)
        newVector[index] += v1[index] + v2[index]

You ensure that len(v1) > len(v2), but then iterate over range(len(v1)).

In your example, you're trying to access v2[2], which doesn't exist.

UPDATE:

In response to your edit, you could use something like this:

def addVectors(v1, v2):
    if len(v1) > len(v2):
        map(sum, zip(v1, v2)).extend(v1[len(v2):])
    else:
        map(sum, zip(v1, v2)).extend(v2[len(v1):])

Comments

0

Your IndexError is because you're trying to write to newVector[index] when newVector is an empty list. You need to either initialize it to a bunch of zeros, or use append instead.

>>> first = [1,2,3]
>>> second = [1,2]
>>> output = []
>>> for i, item in enumerate(first):
...   additional = second[i] if i < len(second) else 0
...   output.append(item + additional)
...
>>> output
[2, 4, 3]

And to ensure that len(first) > len(second), you can do something like this:

first, second = first, second if len(first) > len(second) else second, first

Comments

0

Or you can try

def add_vector(vector1, vector2):
index = len(vector1) - 1
new = []
while index >= 0:
    result = vector1[index] + vector2[index]
    new.append(result)
    index -=1
new.reverse()
return new

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.