I want to create sublist based on looping, but still not find the logic on how to do it?
''' source list'''
list = [1,2,3,4,5,6,7,8,9]
''' sublist goals'''
list_1 = [1,4,7]
list_2 = [2,5,8]
list_3 = [3,6,9]
Just create a 3x3 list and then append items to the list according to the condition
li = [1,2,3,4,5,6,7,8,9]
#Create a 3x3 list
res = [ [] for _ in range(3)]
for idx in range(len(li)):
#Append elements accordingly
index = int(idx%3)
res[index].append(li[idx])
print(res)
The output will look like
[[1, 4, 7],
[2, 5, 8],
[3, 6, 9]]
list = [1,2,3,4,5,6,7,8,9]
list_1 = []
list_2 = []
list_3 = []
for j in range(1,4):
for i in range(j,len(list)+1,3):
if j == 1:
list_1.append(i)
if j == 2:
list_2.append(i)
if j == 3:
list_3.append(i)
print (list_1)
print (list_2)
print (list_3)
output:
[1, 4, 7]
[2, 5, 8]
[3, 6, 9]
In addition to what others have posted you could create a dictionary with the name of the list as the key and the list as the values like this:
>>> for i in range(3):
... d["list_{}".format(i)] = [list[i], list[i+3], list[i+6]]
...
>>> d
{'list_2': [3, 6, 9], 'list_1': [2, 5, 8], 'list_0': [1, 4, 7]}```
Did any one consider this?
>>> list=[1,2,3,4,5,6,7,8,9]
>>> list_1 = list[0::3]
>>> list_2 = list[1::3]
>>> list_3 = list[2::3]
>>> list_1
[1, 4, 7]
>>> list_2
[2, 5, 8]
>>> list_3
[3, 6, 9]
A loop would look like this
for i in range(0,3):
list_i = list[i::3]
print(list_i)
Related
list = [ ["Eggs", "Milk", "Cheese"], [1, 2, 3, 4], ["A", "B" ] ]
newlist = []
appendThisList = []
for count in range(0, 13):
appendThisList.append(count)
if int(count) % 3 == 0:
newlist.append(appendThisList)
appendThisList.clear()
list.append(newlist)
print(list)
Output:
[['Eggs', 'Milk', 'Cheese'], [1, 2, 3, 4], ['A', 'B'], [[], [], [], [], []]]
expected:
[['Eggs', 'Milk', 'Cheese'], [1, 2, 3, 4], ['A', 'B'], [[1,2,3], [4,5,6], [7,8,9], [1,11,12] ]
The issue is here.
if int(count) % 3 == 0:
newlist.append(appendThisList)
appendThisList.clear()
Right code should be:
from copy import copy
if int(count) % 3 == 0:
newlist.append(copy(appendThisList))
appendThisList.clear()
Explanation: You always add the same instance of the list appendThisList to the result. And when you clear it, it clears everywhere even after adding.
Proof:
>>> a = []
>>> b = []
>>> b.append(a)
>>> b
[[]]
>>> a.append('1')
>>> b
[['1']]
>>> a.pop()
'1'
>>> b
[[]]
>>>
I noticed two errors.
First you should start your range from 1, otherwise 0 will be added to your list.
Then as already mentioned by #mrvol, you're clearing the list you have freshly appended. You don't necessarily have to import copy though. Unpacking will do as well:
list = [ ["Eggs", "Milk", "Cheese"], [1, 2, 3, 4], ["A", "B" ] ]
newlist = []
appendThisList = []
for count in range(1, 13):
appendThisList.append(count)
if int(count) % 3 == 0:
newlist += [[*appendThisList]]
appendThisList.clear()
list.append(newlist)
print(list)
Output:
[['Eggs', 'Milk', 'Cheese'], [1, 2, 3, 4], ['A', 'B'], [[1, 2, 3], [4, 5, 6], [7, 8, 9], [10, 11, 12]]]
I have a nested list in the form of [[1,2,3], [3,4,5], [8,6,2,5,6], [7,2,9]]
I would like to extract every first item into a new list, every second item into a new list and the rest into a new nested list:
a = [1,3,8,7] b = [2,4,6,2], c = [[3], [5], [2,5,6],[9]]
Is it possible to avoid using the for loop because the real nested list is quite large? Any help would be appreciated.
Ultimately, whatever your solution would be, you're gonna have to have a for loop inside your code and my advice would be to make it as clean and as readable as possible.
That being said, here's what I would propose:
arr = [[1,2,3], [3,4,5], [8,6,2,5,6], [7,2,9]]
first_arr, second_arr, third_arr = [], [], []
for nested in arr:
first_arr.append(nested[0])
second_arr.append(nested[1])
third_arr.append(nested[2:])
This is a naive, simple looped solution using list comprehensions, but see if it is fast enough for you.
l = [[1,2,3], [3,4,5], [8,6,2,5,6], [7,2,9]]
a = [i[0] for i in l]
b = [i[1] for i in l]
c = [i[2:] for i in l]
which returns:
>>a
[1, 3, 8, 7]
>>b
[2, 4, 6, 2]
>>c
[[3], [5], [2, 5, 6], [9]]
At the moment I cannot think a solution without for loops, I hope I will be able to update my answer later.
Here's a solution using for loops:
data = [[1,2,3], [3,4,5], [8,6,2,5,6], [7,2,9]]
list1 = []
list2 = []
list3 = []
for item in data:
else_list = []
for index, value in enumerate(item):
if index == 0:
list1.append(value)
elif index == 1:
list2.append(value)
else:
else_list.append(value)
list3.append(else_list)
print(list1)
print(list2)
print(list3)
Output
[1, 3, 8, 7]
[2, 4, 6, 2]
[[3], [5], [2, 5, 6], [9]]
Just for fun I share also a performance comparison, great job in using just one for loop Meysam!
import timeit
# a = [1,3,8,7] b = [2,4,6,2], c = [[3], [5], [2,5,6],[9]]
def solution_1():
data = [[1, 2, 3], [3, 4, 5], [8, 6, 2, 5, 6], [7, 2, 9]]
list1 = []
list2 = []
list3 = []
for item in data:
else_list = []
for index, value in enumerate(item):
if index == 0:
list1.append(value)
elif index == 1:
list2.append(value)
else:
else_list.append(value)
list3.append(else_list)
def solution_2():
arr = [[1, 2, 3], [3, 4, 5], [8, 6, 2, 5, 6], [7, 2, 9]]
first_arr, second_arr, third_arr = [], [], []
for nested in arr:
first_arr.append(nested[0])
second_arr.append(nested[1])
third_arr.append(nested[2:])
def solution_3():
l = [[1, 2, 3], [3, 4, 5], [8, 6, 2, 5, 6], [7, 2, 9]]
a = [i[0] for i in l]
b = [i[1] for i in l]
c = [i[2:] for i in l]
if __name__ == "__main__":
print("solution_1 performance:")
print(timeit.timeit("solution_1()", "from __main__ import solution_1", number=10))
print("solution_2 performance:")
print(timeit.timeit("solution_2()", "from __main__ import solution_2", number=10))
print("solution_3 performance:")
print(timeit.timeit("solution_3()", "from __main__ import solution_3", number=10))
Output
solution_1 performance:
9.580000000000005e-05
solution_2 performance:
1.7200000000001936e-05
solution_3 performance:
1.7499999999996685e-05
Suppose the nested list has unknown depth, then we'd have to use recursion
def get_elements(l):
ret = []
for elem in l:
if type(elem) == list:
ret.extend(get_elements(elem))
else:
ret.append(elem)
return ret
l = [1,2,[3,4],[[5],[6]]]
print(get_elements(l))
# Output: [1, 2, 3, 4, 5, 6]
Though it is not quite recommended to use unknown-depth nested lists in the first place.
I have this nested list:
list_1 = [[1,2,3], [1,2,3,4,5,6], [1,2,3,4,5,6,7,8,9]]
Count of sublist elements are always in mulitple of 3. I want to have 3 elments in each sublist. Desired output:
list_1 = [[1,2,3], [1,2,3], [4,5,6],[1,2,3], [4,5,6], [7,8,9]]
I can achieve this but first i have to flatten the list and then create the nested list. My code:
list_1 = [values for sub_list in lists_1 for values in sub_list] # flatten it first
list_1 = [list_1[i:i+3] for i in range(0, len(list_1), 3)]
Is there a way to skip the flatten step and get the desired result?
You can use a nested list comprehension:
list_1 = [[1,2,3], [1,2,3,4,5,6], [1,2,3,4,5,6,7,8,9]]
result = [i[j:j+3] for i in list_1 for j in range(0, len(i), 3)]
Output:
[[1, 2, 3], [1, 2, 3], [4, 5, 6], [1, 2, 3], [4, 5, 6], [7, 8, 9]]
Here is how you can use nested list comprehensions:
list_1 = [[1,2,3],[1,2,3,4,5,6],[1,2,3,4,5,6,7,8,9]]
list_1 = [a for b in list_1 for a in b]
list_1 = [list_1[i:i+3] for i in range(0,len(list_1),3)]
print(list_1)
Output:
[[1, 2, 3], [1, 2, 3], [4, 5, 6], [1, 2, 3], [4, 5, 6], [7, 8, 9]]
To put my two cents in, you could use two generator functions, one that flattens the list (with an arbitrarly nested list) and one that yields pairs of n values:
def recursive_yield(my_list):
for item in my_list:
if isinstance(item, list):
yield from recursive_yield(item)
else:
yield item
def taken(gen, number = 3):
buffer = []
for item in gen:
if len(buffer) < number:
buffer.append(item)
else:
yield buffer
buffer = []
buffer.append(item)
if buffer:
yield buffer
result = [x for x in taken(recursive_yield(list_1))]
Here are some examples of the in- / outputs:
list_1 = [[1,2,3], [1,2,3,4,5,6], [1,2,3,4,5,6,7,8,9]]
# -> [[1, 2, 3], [1, 2, 3], [4, 5, 6], [1, 2, 3], [4, 5, 6], [7, 8, 9]]
list_1 = [1,2,3,4,5,6]
# -> [[1, 2, 3], [4, 5, 6]]
list_1 = [1,2,[[1,2,4,5], [[[[1,10,9]]]]]]
# -> number = 5
# -> [[1, 2, 1, 2, 4], [5, 1, 10, 9]]
Thus, the solution is much more flexible than slicing alone.
Say I have this code:
Num = [[1,2,3], [4,5,6], [7,8,9]]
And I would like to output this:
[ [],[],[] ]
Taking in mind that this is a 2D array, how do I remove all elements from it?
I was thinking of using something like (for i in Num) but nothing came to mind
You can use a for loop:
for x in num:
x.clear()
This will retain the original objects in num, i.e. no new objects are inserted. This might be critical if other objects keep references to those in num and would then run out of sync. For example:
num = [[1, 2, 3], [4, 5, 6], [7, 8, 9]]
ref = num[0]
num = [[] for __ in num]
print(ref) # Still [1, 2, 3].
By using x.clear() on each element of num you ensure that any references stay synced:
num = [[1, 2, 3], [4, 5, 6], [7, 8, 9]]
ref = num[0]
for x in num:
x.clear()
print(ref) # Now [].
This should work:
Num = [[1,2,3], [4,5,6], [7,8,9]]
for i in range(len(Num)):
Num[i].clear()
print(Num)
This would output in:
[[], [], []]
You can do a list-comprehension:
Num[:] = [[] for _ in Num]
This clears all elements still retaining empty lists without creating a new object.
_ (underscore) is "I don’t care" field used as a throw away item.
Try it with list comprehension:
Num = [[] for _ in Num]
I am expecting you to get something like this:
[[], [], []]
To do that, you can do something like:
b = [[1,2,3], [4,5,6], [7,8,9]]
for i in range(len(b)):
b[i] = []
Try this one-liner:
Num = [[1, 2, 3], [4, 5, 6], [7, 8, 9]]
result = [[] for i in Num]
print(result)
Output :
[[], [], []]
so I was working on a piece of code today and I was wondering if there was any "easier" way to divide a list into two without knowing the length of the list.
Here's what I've done:
#say that myList = [0,1,2,3,4,5,6]
tran = 0
L1 = []
L2 = []
while (len(myList) > 0):
tran = myList.pop(0)
L1.append(tran)
if (len(myList) > 0):
tran = myList.pop(0)
L2.append(tran)
I would also like to mention that I'd like each list to take the first value from myList by it's turn. The outcome i'd like to get from this example:
L1 = [0,2,4,6]
L2 = [1,3,5]
You can do something equivalent with slices:
>>> mylist = range(7)
>>> mylist
[0, 1, 2, 3, 4, 5, 6]
>>> a,b = mylist[::2],mylist[1::2]
>>> a
[0, 2, 4, 6]
>>> b
[1, 3, 5]
How about this :
>>> dd = defaultdict(list)
>>> z = [ dd[x].append(y) for x,y in [(('a',i),('b',i))[i % 2] for i in range(1,10)] ]
>>> dd.items()
[('a', [2, 4, 6, 8]), ('b', [1, 3, 5, 7, 9])]
>>>