4

I'm trying to increment a python list of numbers like an abacus.

list = [0,0,0,0]
units = 4

def m(list, units):
  for e in range(len(list)):
    if units:
      list[e] = list[e] + 1
      units -= 1

This code works fine in that if I run m(list, units) the list will be [1,1,1,1] -- the problem I am trying to solve is that when the units value is something like units = 2 the list will increment to [2,2,1,1] (which again is fine) the problem is when I run the m()function from an uneven list, the list will increment from list[0] to end up [3,3,1,1] rather than [2,2,2,2].

Is there a pythonic way I can have the function increment the list from the lowest value to achieve an even spread?

7
  • 2
    Do you mean you want to start from list.index(min(list)) (FYI, list is not a good name for a list, as it shadows the built-in)? Commented Jun 20, 2015 at 14:58
  • Yes, jon - that's exactly it, I'd like to start from the min index -- and I only used the "list" name to make the question easier to read --- thanks -- is there a good way to start from the lowest index of the list? Commented Jun 20, 2015 at 15:02
  • Yes, there is - take the snippet I've provided and figure out where to plug it in. Commented Jun 20, 2015 at 15:03
  • Ah, perfect Jon -- question answered perfectly -- know exactly where to put it - thank you. Commented Jun 20, 2015 at 15:05
  • I'm new - how do I mark this as answered? Commented Jun 20, 2015 at 15:07

1 Answer 1

1

In order to begin at the first element with the minimum value, you can set the starting index to starting_index = abacus.index(min(abacus)) as @jonrsharpe suggests.

However, you need to avoid going beyond the end of the list, for example if units = 4 and starting_index = 3, so you should take the remainder of your calculated index after dividing by len(abacus), i.e. calculated_index % len(abacus).

Finally, I think it would be easier just to loop over range(units). That way you don't need to decrement units yourself, and can handle adding more units at once than the length of the abacus.

Here is an example implementation:

def m(abacus, units):
    starting_index = abacus.index(min(abacus))
    for raw_index in range(units):
        index = (raw_index + starting_index) % len(abacus)
        abacus[index] = abacus[index] + 1

And test:

abacus = [0,0,0,0]    
print abacus
m(abacus, 2)
print abacus
m(abacus, 4)
print abacus
m(abacus, 3)
print abacus
m(abacus, 3)
print abacus
m(abacus, 7)
print abacus

With result:

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

2 Comments

This solution is so beautiful it nearly made me cry. Thanks! Question answered! -- My solution was a horrible bunch of if else statements to decide when the index started -- your solution is much more verbose and "pythonic" thanks again.
This line is great: index = (raw_index + starting_index) % len(abacus) -- Very elegant statement. Wonderful.

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.