6

I was trying to insert list values from one list to another, but in a specific order, where dates[0] entered text[1], dates[1] entered text[3] and so on.

dates=['21/11/2044', '31/12/2018', '23/9/3000', '25/12/2007']

text=['What are dates? ', ', is an example.\n', ', is another format as
well.\n', ', also exists, but is a bit ludicrous\n', ', are examples but more commonly used']

I tried this method:

for j in range(len(text)):
  for i in range(len(dates)):
   text.insert(int((j*2)+1), dates[i])

This was the result, which was incorrect:

['What are dates? ', '25/12/2007', '23/9/3000', '25/12/2007', '23/9/3000',
'25/12/2007', '23/9/3000', '25/12/2007', '23/9/3000', '25/12/2007',
'23/9/3000', '31/12/2018', '21/11/2044', '31/12/2018', '21/11/2044',
'31/12/2018', '21/11/2044', '31/12/2018', '21/11/2044', '31/12/2018',
'21/11/2044', ', is an example.\n', ', is another format as well.\n', ',
also exists, but is a bit ludicrous\n', ', are examples but more commonly used']

I was trying to get back a list that reads like:

['What are dates? ','21/11/2044', 'is an example.\n','31/12/2018', ', is
another format as well.\n','23/9/3000', ', also exists, but is a bit
ludicrous\n', '25/12/2007',', are examples but more commonly used']

Is there a way to insert dates[i] into text[2*j+1] in the way I wanted? Should I even use a for loop, or is there another way without listing everything in dates as well?

6 Answers 6

4

A simpler way to achieve this is using itertools.zip_longest in Python 3.x (or izip_longest in Python 2.x) as:

>>> from itertools import zip_longest # for Python 3.x

>>> # For Python 2.x
>>> # from itertools import izip_longest

>>> dates=['21/11/2044', '31/12/2018', '23/9/3000', '25/12/2007']
>>> text=['What are dates? ', ', is an example.\n', ', is another format as well.\n', ', also exists, but is a bit ludicrous\n', ', are examples but more commonly used']

>>> [w for x in zip_longest(text, dates, fillvalue='') for w in x if w]
['What are dates? ', '21/11/2044', ', is an example.\n', '31/12/2018', ', is another format as well.\n', '23/9/3000', ', also exists, but is a bit ludicrous\n', '25/12/2007', ', are examples but more commonly used']

The issue with your code is that you have nested for loops, and that's why for each index of j, all values of dates are getting added.

Sign up to request clarification or add additional context in comments.

2 Comments

Thank you for the reply, the code works as intended. However, I was doing a project in Al Sweigart's book, where I used regular expressions to find dates of different formats, i.e. 5/14/2000, 2016/5/16, replace them in a standard format, D/M/Y. The book hinted using the regex.sub() function to find and replace these unstandardised date formats, and I used :'foregex=re.compile(r'\d{1,4}/\d{1,2}/\d{1,4}') for i in range(len(dates)): print(foregex.sub(dates[i], text)) , which didn't work. Is there any way to use the info from previous chapters (currently chap. 7) to get my intended list?
You'll have to write a very smart regex in order to identify the difference between " 5/14/2000" and "2016/5/16" because Python doesn't know what is the year, and what is the month. For Python all are strings. Simpler way to do it is using dateutil library as used here: stackoverflow.com/a/470303/2063361 .However if you want to regex only, you should create a separate question, and the community, I am noot that good in regex :)
1

For your specific example of wanting to fit the dates in every other element you can use zip:

parts = zip(['a', 'b', 'c', 'd'], ['d1', 'd2', 'd3'])
text = [x for y in parts for x in y]
# ['a', 'd1', 'b', 'd2', 'c', 'd3']

You may need to use itertools.izip_longest and/or handle unequal lengths between the list or you'll see results like the above where 'd' was left off the end. The second line is ugly list comprehension magic to flatten a list of lists.

2 Comments

zip will skip the last element from one the list here
Yep, that's why I mentioned that that would happen. I upvoted your answer since you took the time to do the full answer instead of my shortcut.
0

The double for loop is the problem here; just using a single for loop, as in

for i in range(len(dates)):
    text.insert(int((i*2)+1), dates[i])

should do the trick.

However, if you are planning on the second list ending up as a string, it might be simpler to use .format, as in

text = 'Date with one format is {} and date with another format is {}.'.format(*dates)

which will give you

'Date with one format is 21/11/2044 and date with another format is 31/12/2018.'

Comments

0

Maybe it is not the most elegant version, but this works for example:

from itertools import zip_longest


dates=['21/11/2044', '31/12/2018', '23/9/3000', '25/12/2007']

text=['What are dates? ', ', is an example.\n', ', is another format as well.\n', ', also exists, but is a bit ludicrous\n', ', are examples but more commonly used']


l3 = list()
for i, j in zip_longest(text, dates, fillvalue=None):
    if i is not None:
        l3.append(i)
    if j is not None:
        l3.append(j)

print(l3)

zip_longest from the standard itertools module zips 2 lists of uneven length together and fills the missing values with "fillvalue". If you just discard that fillvalue, you are good to go.

Comments

0

A simple solution which is pretty easy to understand

counter = 0
while counter < len(dates):
    text.insert(counter + counter + 1, dates[counter])
    counter += 1

Essentially, .insert() is used to just append to a list in a specific position.

Comments

0

You can use:

result = [ ]
for x in enumerate(dates, text):
   result.append(dates[x]).append(text[x])

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.