简体   繁体   中英

How to convert every even number in a list to odd

one of my revision questions was to create a func that takes a list of integer values as a list, and convert every even number into an odd number.

Expected Output:
integer_list = [1, 2, 3, 4, 5, 6, 7]
Before: [1, 2, 3, 4, 5, 6, 7]
After: [1, 3, 3, 5, 5, 7, 7]

integer_list = [1, -2, 3, -4, 8, 16, 21, -17]
Before: [1, -2, 3, -4, 8, 16, 21, -17]
After: [1, -3, 3, -5, 9, 17, 21, -17]

Code thus far:

def make_all_odd(integer_list):
    for number in integer_list:
        if (number % 2) == 0:
            number += 1
            integer_list.append(number)

So far, I've only figured out that I need to iterate through every element in the list and check if it is even using a for loop, but I'm not sure how to modify the original string to change the identified even numbers into odd. I know my code just adds the recently converted even to odd numbers to the end of the list, but in my case I have to replace, not add. I first thought of using find() but that doesn't work for lists

You're making a critical mistake: You're modifying a list while you are iterating it . Don't do that. Sometimes the language or implementation will save you, but often times you'll end up getting strange and incorrect results.

Try instead iterating over the list by index:

for i in range(len(integer_list)):
   # You can read an item from the list:
   val = integer_list[i]

   # And you can overwrite an item in the list:
   integer_list[i] = new_val

(The exact solution is up to you to come up with.)

You can modify a list using this syntax: list[index] = whatever you want here . Indexes start at 0. Enumerate just allows you to get the index while looping, instead of doing list.index(element) .

Code:

Using Enumerate:

integer_list = [1, 2, 3 , 4, 5, 6, 7]
def make_all_odd(integer_list):
    for index, number in enumerate(integer_list):
        if (number % 2) == 0:
            integer_list[index] += 1

make_all_odd(integer_list)
print(integer_list)

Without Using Enumerate (doesn't take into account duplicate value, so the even numbers all have to be different):

integer_list = [1, 2, 3 , 4, 5, 6, 7]
def make_all_odd(integer_list):
    for number in integer_list:
        index = integer_list.index(number)
        if (number % 2) == 0:
            integer_list[index] += 1

make_all_odd(integer_list)
print(integer_list)

Here I use a variable to keep track of the index instead of the .index method, and this fixes not being able to use duplicates.

integer_list = [1, 2, 3 , 4, 5, 6, 7]
index = 0
def make_all_odd(integer_list):
    for number in integer_list:
        index = integer_list.index(number)
        if (number % 2) == 0:
            integer_list[index] += 1
    index+=1

make_all_odd(integer_list)
print(integer_list)

You could also do this return a new list (if you don't want the original list to be modified):

Returning New List Using Enumerate:

integer_list = [1, 2, 3 , 4, 5, 6, 7]
def make_all_odd(integer_list):
    integer_list_copy = integer_list.copy() # remember to use .copy(), look at https://stackoverflow.com/questions/2612802/list-changes-unexpectedly-after-assignment-why-is-this-and-how-to-prevent-it 
    for index, number in enumerate(integer_list):
        if (number % 2) == 0:
            integer_list_copy[index] = number + 1
    return integer_list_copy

make_all_odd(integer_list)
print(integer_list)

Also, don't change a list when iterating through it. It just gives everyone headaches.

Keep it simple using the True/False array:

import numpy as np
L = [1, 2, 3, 4, 5, 6, 7]
L + (np.mod(L,2)==0)

which returns:

array([1, 3, 3, 5, 5, 7, 7])

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM