Create a new list by taking the first item from the first list and the last item from the second list

How do I scroll my 2 lists to use

a=[1,2,3,8,12] b=[2,6,4,5,6] 

To obtain

 [1,6,2,5,3,8,6,12,2] 

OR use

 d=[a,b,c,d] e=[w,x,y,z] 

To obtain

 [a,z,b,y,c,x,d,w] 

(1st item from the 1st list, last item from the 2nd list)
(2nd item from the 1st list, 2nd to the last item from the 2nd list)

+7
python list
source share
4 answers
 [value for pair in zip(a, b[::-1]) for value in pair] 
+11
source share

You can archive the first list with the opposite sign of the second (using itertools.izip_longest ), and then join the columns using itertools.chain :

 >>> d=['a','b','c','d'] >>> e=['w','x','y','z'] >>> >>> from itertools import chain, zip_longest # in python 2 use izip_longest >>> >>> list(chain(*izip_longest(d, e[::-1]))) ['a', 'z', 'b', 'y', 'c', 'x', 'd', 'w'] 

The advantage of using zip_longest() is that it accepts the fillvalue argument, which will be passed to fill the omitted elements when your lists are not equal in length.

If you are sure that the length of the lists is the same, you are better off using the built-in zip() function.

 >>> d=['a','b'] >>> e=['w','x','y','z'] >>> list(chain(*izip_longest(d, e[::-1], fillvalue=''))) ['a', 'z', 'b', 'y', '', 'x', '', 'w'] 

More pythonic method suggested by @Jon Clements:

 list(chain.from_iterable(zip_longest(d, reversed(e)))) 
+5
source share

Well, I did some tests for python2:

 import time from operator import itemgetter from itertools import chain, izip_longest a = [1, 2, 3, 8, 12] b = [2, 6, 4, 5, 6] print "Using value and zip" starttime = time.time() c = [value for pair in zip(a, b[::-1]) for value in pair] elapsed = time.time() - starttime print c print elapsed print "Using chain and izip" starttime = time.time() c = list(chain(*izip_longest(a, b[::-1]))) elapsed = time.time() - starttime print c print elapsed print "Using itemgetter" c = [] starttime = time.time() for i in xrange(0, len(a)): c.append(itemgetter(i)(a)) c.append(itemgetter(len(b)-i-1)(b)) elapsed = time.time() - starttime print c print elapsed 

exit:

 Using value and zip [1, 6, 2, 5, 3, 4, 8, 6, 12, 2] 1.59740447998e-05 Using chain and izip [1, 6, 2, 5, 3, 4, 8, 6, 12, 2] 3.2901763916e-05 Using itemgetter [1, 6, 2, 5, 3, 4, 8, 6, 12, 2] 1.4066696167e-05 

Sometimes the first method is faster, and sometimes the third.

These are the results for lenght = 1000 lists:

 Using value and zip 0.000767946243286 Using chain and izip 0.000431060791016 Using itemgetter 0.00203609466553 

As you can see, the second method improves for longer lists.

0
source share

How about this:

 a=[1,2,3,8,12] b=[2,6,4,5,6] >>> a1 = list(map(lambda x: a1.extend([x,0]), a)) [None, None, None, None, None] >>> a1 [1, 0, 2, 0, 3, 0, 8, 0, 12, 0] >>> b1 = list(map(lambda x: b1.extend([0,x]), b[::-1])) [None, None, None, None, None] >>> b1 [0, 6, 0, 5, 0, 4, 0, 6, 0, 2] >>> c = [x+y for x,y in zip(a1,b1)] >>> c [1, 6, 2, 5, 3, 4, 8, 6, 12, 2] 

If a and b have different lengths, then:

 >>> c = [x+y for x,y in izip_longest(a1,b1)] #you choose your fillvalue. 
0
source share

All Articles