aList = []
for number in range (1,11):
aList += [number]
print ("printing",aList);
Output is:
printing
[1, 2, 3, 4, 5, 6, 7, 8, 9, 10]
but if I modify like this (I expect 100 to be added to the end of the list)
aList = []
for number in range (1,11):
aList += [number]
aList += 100;
print ("printing",aList);
I get this error: TypeError: 'int' object is not iterable
You have three problems with your current code:
aList += 100 should be aList += [100]
You should remove all of the semicolons
aList += [100] should be moved to outside the for loop
For example:
In [2]:
aList = []
for number in range (1,11):
aList += [number]
aList += [100]
print ("printing",aList) # ('printing', [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 100])
You could also simply this to:
print ("printing", range(1, 11) + [100]) # ('printing', [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 100])
If you don't want to use .append() on a list:
aList = []
for number in range (1,11):
aList += [number]
aList += [100]
print ("printing",aList)
Please note that you don't need the semicolon at the end of the line (;)
range returns a list, hence this much is sufficient instead of for loop
aList = range(1, 11)
to add '100' as last element, add one more statement
aList += [100]
or
aList.append(100)
range is a list. Hence, you can just do:
aList = range(10) + [100]
Related
I am iterating in a for loop, constructing a list, whilst comparing the last number of that list with another number.
I would like my code to see if the last item of the list is smaller than the item it is being compared to, and if it is, to add it to the end of its list and then to continue.
if the last item of the list is larger, i would like to pop off the last item of the list. i would then like to subject it to the same conditionals.
here is my code, it is not working, it wont re check the conditionals after popping off the last item of the list.
if tempList:
lastNum=tempList[-1]
#############################################
if element < lastNum:
incList.append(tempList)
tempList.pop()
lastNum=tempList[-1]
#############################################
elif lastNum < element:
tempList.append(element)
continue
You can bundle this into a function:
def append_if_lower_else_pop_end_from_list_until_lower(l, num):
"""Add num to l if l[-1] < num, else pop() from l until"""
while l and l[-1] > num:
l.pop()
l.append(num)
# this is not strictly needed - lists are mutable so you are mutating it
# returning it would only make sense for chaining off it with other methods
return l
k = [3,5,7,9,11,13]
print(k)
append_if_lower_else_pop_end_from_list_until_lower(k, 10)
print(k)
append_if_lower_else_pop_end_from_list_until_lower(k, 6)
print(k)
append_if_lower_else_pop_end_from_list_until_lower(k, 10)
print(k)
append_if_lower_else_pop_end_from_list_until_lower(k, 10)
print(k)
append_if_lower_else_pop_end_from_list_until_lower(k, -10)
print(k)
Output:
[3, 5, 7, 9, 11, 13] # start
[3, 5, 7, 9, 10] # after adding 10
[3, 5, 6] # after addding 6
[3, 5, 6, 10] # after adding 10
[3, 5, 6, 10, 10] # after adding 10 again
[-10] # after adding -10
Why return the list as well: example for chaining:
k = [3,5,17,9,11,13]
append_if_lower_else_pop_end_from_list_until_lower(k, 10).sort()
print(k)
Output:
[3, 5, 9, 10, 17]
Try this out:
yourlist = [3,1,4]
n = 1
resultlist = yourlist[:-1] if yourlist[-1]>=n else yourlist+[n]
print(resultlist)
n = 5
resultlist = yourlist[:-1] if yourlist[-1]>=n else yourlist+[n]
print(resultlist)
Output:
[3,1]
[3,1,4,5]
I'm trying to solve this task:
Loop through list A and create a new list with only items form list A that's between 0-5.
What am I doing wrong here?
a = [100, 1, 10, 2, 3, 5, 8, 13, 21, 34, 55, 98]
def new_list(x):
for item in range(len(x)):
new = []
if x[item] < 5 and x[item] > 0:
(new.append(item))
return new
print(new_list(a))
I'm just getting [1] as an answer.
You return command is inside the loop so as soon as it goes through the first case it returns the value exiting the function.
Here is an example of what your code should look like
a = [100, 1, 10, 2, 3, 5, 8, 13, 21, 34, 55, 98]
def new_list(x):
new = []
for item in range(len(x)):
if x[item] < 5 and x[item] > 0:
new.append(x[item])
return new
print new_list(a)
You can achieve the same result by using a list comprehension
def new_list(x):
return [item for item in x if 0 < item < 5]
You're resetting new to a brand new empty list each time through the loop, which discards any work done in prior iterations.
Also, in the if statement you're calling return, which exits your function immediately, so you never process the remainder of the list.
You probably wanted something like this instead:
def new_list(x):
new = []
for item in x:
if 0 < item < 5:
new.append(item)
return new
Just my recommendation. You could use filter() here instead of a making your own loop.
a = [100, 1, 10, 2, 3, 5, 8, 13, 21, 34, 55, 98]
def new_list(x, low=0, high=5):
return filter(lambda f: f in range(low, high), x)
Filter returns a new list with elements passing a given predicate and it's equivalent to
[item for item in iterable if function(item)]
as per the documentation.
Therefore
print new_list(a)
Results in:
[1, 2, 3, 5]
This way you can check any values such as:
print new_list(a, 5, 10)
[5, 8]
Three errors:
you are reinstantiating new with each iteration of the for loop.
you should return new when the list is finished building, at the end of the function.
You are appending item, but this is your index. In your code, you would have to append x[item].
Code with corrections:
a = [100, 1, 10, 2, 3, 5, 8, 13, 21, 34, 55, 98]
def new_list(x):
new = []
for item in range(len(x)):
if x[item] < 5 and x[item] > 0:
new.append(x[item])
return new
print(new_list(a))
Output:
[1, 2, 3]
Suggestions:
Don't index, loop over the items of x directly (for item in x: ...).
Use chained comparisons, e.g. 0 < item < 5.
Consider a list comprehension.
Code with all three suggestions:
>>> [item for item in a if 0 < item < 5]
>>> [1, 2, 3]
Just a suggestion!
The empty list is inside the For Loop meaning that a new empty list is created every iteration
The 'return' is also inside the for loop which is less than ideal, you want it to be returned after the loop has been exhausted and all suitable elements have been appended.
a = [100, 1, 10, 2, 3, 5, 8, 13, 21, 34, 55, 98]
def new_list(x):
new = []
for item in range(len(x)):
if x[item] < 5 and x[item] > 0:
new.append(item)
return new
print(new_list(a))
i need to modify the contents of my og list into a different list w/out actually changing my og list.
def createList(numbers):
my_List= [0] * numbers
for q in range(0, len(my_List)):
myList[q]= randint (1, 21)
q=q+1
return my_List
def modifyList(newList):
for i in range(0, len(newList)):
if i % 2 == 0:
newList[i]= newList[i] / 2
else:
newList[i]= newList[i] * 2
return newList
def main():
my_List= createList(10)
print my_List
newList= modifyList(my_List)
print my_List
print newList
You need to make a copy of the list that is inputted to the modifyList function. This copy isn't done with myList[:] as you are not working with myList here! You are working with a different variable called newList which you need to make a copy of.
You need to remember that a function works with a variable that is passed into it but under the name it has been assigned in the function definition. So here, even though you only call the function with modifyList(myList), inside the function, you are always working with newList so trying to do anything with myList here will throw an error saying its undefined.
def modifyList(newList):
newList = newList[:]
for j in range(0, len(newList)):
if j % 2 == 0:
newList[j]= newList[j] / 2
else:
newList[j]= newList[j] * 2
return newList
Here's an alternate way, with list comprehensions. In Python, you usually don't have to create a list with placeholders and put the elements one by one:
>>> from random import randint
>>> my_list = [randint(1, 20) for _ in range(10)]
>>> my_list
[1, 20, 2, 4, 8, 12, 16, 7, 4, 14]
>>> [x * 2 if i % 2 else x / 2 for i, x in enumerate(my_list)]
[0.5, 40, 1.0, 8, 4.0, 24, 8.0, 14, 2.0, 28]
If you want to modify the original list in place, you could use numpy and advanced slicing:
>>> import numpy as np
>>> a = np.array([11, 13, 21, 12, 18, 2, 21, 1, 5, 9])
>>> a[::2] = a[::2] / 2
>>> a[1::2] = a[1::2] * 2
>>> a
array([ 5, 26, 10, 24, 9, 4, 10, 2, 2, 18])
def every_other (l):
alist = []
alist = l
for i in range (len (l)-1):
print (i)
if i % 2 == 1:
del (alist [i])
print (alist)
every_other ([0, -12, 4, 18, 9, 10, 11, -23])
output is [0, 4, 18, 10, 11]
when it should be: [0, 4, 9, 11]
Thanks in advance.
You can't remove items from a list and iterate through it at the same time, because that confuses the iterator. Either create a new list and add to it instead of removing items from the old one, or you can use Python's slice syntax to do this in one operation:
def every_other(l):
print l[::2]
Also, you can use list comprehension and filter the list based on its count:
the_list = [0, -12, 4, 18, 9, 10, 11, -23]
new_list = [i for a, i in enumerate(the_list) if a%2 == 0]
Below code will solve your logic:
a=[0, -12, 4, 18, 9, 10, 11, -23]
l=[]
for i,x in enumerate(a):
print "index : ",i,"data : ",x,">>>",i%2
if i%2!=1:
l.append(x)
you are deleting the same list that you are trying to iterate.so when your are at index 1 you delete-12 your new list is [0,4, 18, 9, 10,11,-23]
now you reach index 2 of iteration your value is 18 so its not deleted and same logic continues till the iteration completes.
This code should work if you only want to iterate every other element in a list;
def every_other(l):
return l[0::2]
But if you want to remove every other element then you should do that first before you print or return the list.
def remove_every_other(my_list):
del my_list[1::2]
return my_list
I am trying to do the following..
I have a list of n elements. I want to split this list into 32 separate lists which contain more and more elements as we go towards the end of the original list. For example from:
a = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12]
I want to get something like this:
b = [[1],[2,3],[4,5,6,7],[8,9,10,11,12]]
I've done the following for a list containing 1024 elements:
for i in range (0, 32):
c = a[i**2:(i+1)**2]
b.append(c)
But I am stupidly struggling to find a reliable way to do it for other numbers like 256, 512, 2048 or for another number of lists instead of 32.
Use an iterator, a for loop with enumerate and itertools.islice:
import itertools
def logsplit(lst):
iterator = iter(lst)
for n, e in enumerate(iterator):
yield itertools.chain([e], itertools.islice(iterator, n))
Works with any number of elements. Example:
for r in logsplit(range(50)):
print(list(r))
Output:
[0]
[1, 2]
[3, 4, 5]
[6, 7, 8, 9]
... some more ...
[36, 37, 38, 39, 40, 41, 42, 43, 44]
[45, 46, 47, 48, 49]
In fact, this is very similar to this problem, except it's using enumerate to get variable chunk sizes.
This is incredibly messy, but gets the job done. Note that you're going to get some empty bins at the beginning if you're logarithmically slicing the list. Your examples give arithmetic index sequences.
from math import log, exp
def split_list(_list, divs):
n = float(len(_list))
log_n = log(n)
indices = [0] + [int(exp(log_n*i/divs)) for i in range(divs)]
unfiltered = [_list[indices[i]:indices[i+1]] for i in range(divs)] + [_list[indices[i+1]:]]
filtered = [sublist for sublist in unfiltered if sublist]
return [[] for _ in range(divs- len(filtered))] + filtered
print split_list(range(1024), 32)
Edit: After looking at the comments, here's an example that may fit what you want:
def split_list(_list):
copy, output = _list[:], []
length = 1
while copy:
output.append([])
for _ in range(length):
if len(copy) > 0:
output[-1].append(copy.pop(0))
length *= 2
return output
print split_list(range(15))
# [[0], [1, 2], [3, 4, 5, 6], [7, 8, 9, 10, 11, 12, 13, 14]]
Note that this code is not efficient, but it can be used as a template for writing a better algorithm.
Something like this should solve the problem.
for i in range (0, int(np.sqrt(2*len(a)))):
c = a[i**2:min( (i+1)**2, len(a) )]
b.append(c)
Not very pythonic but does what you want.
def splitList(a, n, inc):
"""
a list to split
n number of sublist
inc ideal difference between the number of elements in two successive sublists
"""
zr = len(a) # remaining number of elements to split into sublists
st = 0 # starting index in the full list of the next sublist
nr = n # remaining number of sublist to construct
nc = 1 # number of elements in the next sublist
#
b=[]
while (zr/nr >= nc and nr>1):
b.append( a[st:st+nc] )
st, zr, nr, nc = st+nc, zr-nc, nr-1, nc+inc
#
nc = int(zr/nr)
for i in range(nr-1):
b.append( a[st:st+nc] )
st = st+nc
#
b.append( a[st:max(st+nc,len(a))] )
return b
# Example of call
# b = splitList(a, 32, 2)
# to split a into 32 sublist, where each list ideally has 2 more element
# than the previous
There's always this.
>>> def log_list(l):
if len(l) == 0:
return [] #If the list is empty, return an empty list
new_l = [] #Initialise new list
new_l.append([l[0]]) #Add first iteration to new list inside of an array
for i in l[1:]: #For each other iteration,
if len(new_l) == len(new_l[-1]):
new_l.append([i]) #Create new array if previous is full
else:
new_l[-1].append(i) #If previous not full, add to it
return new_l
>>> log_list([1, 2, 3, 4, 5, 6, 7, 8, 9, 10])
[[1], [2, 3], [4, 5, 6], [7, 8, 9, 10]]