Swap and reverse elements in a python list - python

I have a list with elements as following:
L =[1, 2, 3, 4, 5]
I want to mirror and reorder as follows:
L =[1,5,2,4,3]
Numbers and size of elements in the list may vary and change!
Having some other examples,
K=[1, 2, 3]
Output may come out as:
K=[1, 3, 2]
And
D=[1,2,3,4]
Final results:
D = [1,4,2,3]
I have tried to do it with slice, it doesn't work for me.

You can do that by merging the list with its reverse:
lst = [1,2,3,4,5]
b = [c for a,b in zip(lst,reversed(lst)) for c in (a,b)][:len(lst)]
print(b) # [1, 5, 2, 4, 3]

Is this what you're looking for?
from random import shuffle
my_list = [1,2,3,4,5]
print (my_list)
shuffle (my_list)
print (my_list)

The following code gives you the expected output.
l = [1,2,3,4,5]
r = []
for i in range(len(l)):
if i % 2 == 0:
r.append(l[i // 2])
else:
r.append(l[-1 - i // 2])
print(r) # prints [1, 5, 2, 4, 3]

Related

Multiple loop in list comprehension

I have a problem set in hand, the description is something like:
We have 2 lists ie "nums1" and "nums2" and 2 integers m and n
nums1 = [1, 2, 3, 7, 8, 9]
m = 3
nums2 = [2, 5, 6]
n = 2
Here "m" denotes number of elements to be picked from "nums1" and "n" denotes the number of elements to be picked from "nums2".
There are other ways ofcourse, but I want to create a list with only "list comprehension" on the above conditions.
With a simple for loop I can achieve that with:
li = []
for i in range(m):
li.append(nums1[i])
for j in range(n):
li.append(nums2[j])
print(li)
I tried the following but the outcome result is not as expected:
[a for a in nums1 for b in nums2]
Expected output:
[1, 2, 2, 3, 5]
Also, does list comprehension supports multiple loop?
Given the following:
nums1 = [1, 2, 3, 7, 8, 9]
m = 3
nums2 = [2, 5, 6]
n = 2
Using strictly list comprehension, the following does what you asked for:
sorted([nums1[a] for a in range(m)] + [nums2[b] for b in range(n)])
Returns:
[1, 2, 2, 3, 5]
as per the conditions with "List comprehension" to be specific.
Although as others have said in the comment, a slice would have been more pythonic and easier to reason about. But since you asked for a list comprehension implementation, then this is as close to an answer as you'll get.
nums1 = [1, 2, 3, 7, 8, 9]
m = 3
nums2 = [2, 5, 6]
n = 2
ll = sorted([a for b in [nums1[:m], nums2[:n]] for a in b])
print(ll)
Output
[1, 2, 2, 3, 5]
nums1 = [1, 2, 3, 7, 8, 9]
m = 3
nums2 = [2, 5, 6]
n = 2
Create an empty list and store the returned values in this list if you need to access them later on in the program
nums3 = []
[nums3.append(nums1[i]) for i in range(m)]
[nums3.append(nums2[i]) for i in range(n)]
Sorts and prints the newly created list
print(sorted(nums3))

reordering a list based on specific order

I want to reorder a list with length n, where n can be any integer between 5 and 20.
example list = [1,2,3,4,5,6]
for each one of my generated lists, I want to move the last but one element [-2] to the start of the list [0] such that the final order becomes:
new_list = [5,1,2,3,4,6]
I have tried:
myorder =[1,2,3,4,5,6]
new_order = [(myorder[-2]), [i for i in myorder[:-2]], (myorder[-1])]
but this gives me a list in a list:
[5, [1, 2, 3, 4], 6]
Is there a simple way to do this for list comprehension?
You can try this:
new_order = [myorder[-2]] + [i for i in myorder[:-2]] + [myorder[-1]]
Or, simplifying a bit,
new_order = [myorder[-2]] + myorder[:-2] + [myorder[-1]]
You can use list slicing.
Ex:
l = [1,2,3,4,5,6]
print([l[-2]] + l[:-2] + l[-1:])
Output:
[5, 1, 2, 3, 4, 6]
What about this:
>>> lst = [1, 2, 3, 4, 5, 6]
>>> lst = [lst[-2]] + lst[:-2] + [lst[-1]]
>>> lst
[5, 1, 2, 3, 4, 6]
I think this is the most general way of doing it:
example_list.insert(0, example_list.pop(-2))
You erase (pop) item -2 and insert it at position 0.

How to get the expected result using list comprehension

I have the following lists
a=[1,2,3]
b=[4,5,6]
c=[a,b]
i need to combine both list a and b.
result should be like [1,2,3,4,5,6]
i tried with list comprehension
[x for x in i for i in c]
output
[3, 3, 4, 4, 5, 5]
How can i get the result as [1,2,3,4,5,6] using list comprehension.
You can just do:
a + b
If you must use list comprehension:
In [10]: a = [1, 2, 3]
In [11]: b = [4, 5, 6]
In [12]: c = [a, b]
In [13]: [j for i in c for j in i]
Out[13]: [1, 2, 3, 4, 5, 6]
Use itertools.chain.
import itertools
a=[1,2,3]
b=[4,5,6]
c = list(itertools.chain(a, b))
You are concatenating, use + to do so:
c = a + b
If you are concatenating an arbitrary number of lists, use itertools.chain.from_iterable():
from itertools import chain
list_of_lists = [a, b]
c = list(chain.from_iterable(list_of_lists))
Note that if all you need to do is iterate over the concatenation result, you can leave of the list() call altogether.
Do not use sum() for this; that leads to quadratic behaviour as intermediate results are built for every element summed, which takes a full loop.
You can do it with + operation
a = [1, 2, 3]
b = [3, 4, 5]
c = a + b # Equal [1, 2, 3, 3, 4, 5]
Here are 3 different ways you can do it:
>>> a=[1,2,3]
>>> b=[4,5,6]
>>> c=a+b
>>> c
[1, 2, 3, 4, 5, 6]
>>> c=[item for l in [a, b] for item in l]
>>> c
[1, 2, 3, 4, 5, 6]
>>> import itertools
>>> list(itertools.chain(*[a, b]))
[1, 2, 3, 4, 5, 6]

Python: How to combine the results of for loop into one output?

numbers = [1, 2, 3]
for number in numbers:
number = number * 2
#For the output I will get:
2
4
6
How do I modify my code so the results can be combined (eg. [2, 4, 6]) without using the print statement?
Use a list comprehension:
[num*2 for num in numbers]
>>> numbers = [1, 2, 3]
>>> [num*2 for num in numbers]
[2, 4, 6]
>>>
Create new List type variable result and add values into it by list append() method.
Demo:
>>> numbers = [1, 2, 3]
>>> result = []
>>> for i in numbers:
... result.append(i*2)
...
>>> result
[2, 4, 6]
>>>
If you want to gather the results into a list, you just create a list and append each one onto it:
numbers = [1, 2, 3]
doubles = []
for number in numbers:
double = number * 2
doubles.append(double)
… or, more compactly, do the same with a list comprehension:
numbers = [1, 2, 3]
doubles = [number * 2 for number in numbers]

List slicing in python every other value

Suppose I have a list x = [1,2,3] and I want to output every other value than the indexed one, is there a list operation I can use?, ie: x[0]=> [2,3], x[1] => [1,3], x[2] =>[1,2] ?
You could use this:
def exclude(l, e):
return [v for i, v in enumerate(l) if i != e]
>>> exclude(range(10), 3)
[0, 1, 2, 4, 5, 6, 7, 8, 9]
You could do it with a slice, but I'd be tempted to try:
a = [1, 2, 3]
b = a[:]
del b[1]
edit
The above does "technically" use a slice operation, which happens to be on list objects in effect a shallow-copy.
What's more flexible and shouldn't have any downsides is to use:
a = [1, 2, 3]
b = list(a)
del b[1]
The list builtin works on any iterable (while the slice operation [:] works on lists or those that are indexable) so that you could even extend it to constructs such as:
>>> a = '123'
>>> b = list(a)
>>> del b[0]
>>> ''.join(b)
'23'
You could use x[:i] + x[i+1:]:
In [8]: x = [1, 2, 3]
In [9]: i = 0
In [10]: x[:i] + x[i+1:]
Out[10]: [2, 3]
Depending on the context, x.pop(i) might also be useful. It modifies the list in place by removing and returning the i-th element. If you don't need the element, del x[i] is also an option.
>>> x = [1, 2, 3]
>>> x[:1] + x[2:]
[1, 3]
my_list = [1, 2, 3]
my_list.remove(my_list[_index_]) #_index_ is the index you want to remove
Such that: my_list.remove(my_list[0]) would yield [2, 3],
my_list.remove(my_list[1]) would yield [0, 3], and
my_list.remove(my_list[2]) would yield [1, 2].
So you want every value except the indexed value:
Where i is the index:
>>> list = [1,2,3,4,5,6,7,8]
>>> [x for x in list if not x == list[i]]
This will give you a list with no instances of the i't element, so e.g.:
>>> i = 2
>>> list = [1,2,3,4,5,6,7,1,2,3,4,5,6,7]
>>> [x for x in list if not x == list[i]]
[1, 2, 4, 5, 6, 7, 1, 2, 4, 5, 6, 7]
note how 3 is not in that list at all.
Every other is
x[::2], start at 0
x[1::2], start at 1

Categories