Inserting list into another list using loops only: - python-3.x

I'm using the current version of python. I need to return a copy of list1 with list2 inserted at the position indicated by index i.e if the index value is 2, list2 is inserted into list 1 at position 2. I can only use for/while loops, the range function & the list_name.append (value) methods and the lists cannot be sliced. So if list1 list1 = boom list2 = red and the index value = 2, how do I return a new list = boredom? I have this so far:
list1 = ['b','o','o','m']
list2 = ['r','e','d']
index = 2
new_list = []
if index > len(list1):
new_list = list1 + list2
print (new_list)
if index <= 0:
new_list = list2 + list1
print (new_list)

An alternative approach to Padriac's - using three for loops:
list1 = ['b','o','o','m']
list2 = ['r','e','d']
n = 2
new_list = []
for i in range(n): # append list1 until insert point
new_list.append(list1[i])
for i in list2: # append all of list2
new_list.append(i)
for i in range(n, len(list1)): # append the remainder of list1
new_list.append(list1[i])

Once you hit the index, use an inner loop to append each element from list2:
for ind, ele in enumerate(list1):
# we are at the index'th element in list1 so start adding all
# elements from list2
if ind == index:
for ele2 in list2:
new_list.append(ele2)
# make sure to always append list1 elements too
new_list.append(ele)
print(new_list)
['b', 'o', 'r', 'e', 'd', 'o', 'm']
If you must use range just replace enumerate with range:
new_list = []
for ind in range(len(list1)):
if ind == index:
for ele2 in list2:
new_list.append(ele2)
new_list.append(list1[ind])
print(new_list)
['b', 'o', 'r', 'e', 'd', 'o', 'm']
Or without ifs using extend and remove if allowed:
new_list = []
for i in range(index):
new_list.append(list1[i])
list1.remove(list1[i])
new_list.extend(list2)
new_list.extend(list1)
Appending as soon as we hit the index means the elements will be inserted from the correct index, the elements from list1 must always be appended after your if check.

Check out this small snippet of code I've written.
Check the while condition that is used. I hope it will answer your question.
email = ("rishavmani.bhurtel#gmail.com")
email_split = list(email)
email_len = len(email)
email_uname_len = email_len - 10
email_uname = []
a = 0
while (a < email_uname_len):
email_uname[a:email_uname_len] = email_split[a:email_uname_len]
a = a + 1
uname = ''.join(email_uname)
uname = uname.replace(".", " ")
print("Possible User's Name can be = %s " %(uname))

Related

How to get unique values in nested list along single column?

I need to extract only unique sublists based on first element from a nested list. For e.g.
in = [['a','b'], ['a','d'], ['e','f'], ['g','h'], ['e','i']]
out = [['a','b'], ['e','f'], ['g','h']]
My method is two break list into two lists and check for elements individually.
lis = [['a','b'], ['a','d'], ['e','f'], ['g','h']]
lisa = []
lisb = []
for i in lis:
if i[0] not in lisa:
lisa.append(i[0])
lisb.append(i[1])
out = []
for i in range(len(lisa)):
temp = [lisa[i],lisb[i]]
out.append(temp)
This is an expensive operation when dealing with list with 10,00,000+ sublists. Is there a better method?
Use memory-efficient generator function with an auziliary set object to filter items on the first unique subelement (take first unique):
def gen_take_first(s):
seen = set()
for sub_l in s:
if sub_l[0] not in seen:
seen.add(sub_l[0])
yield sub_l
inp = [['a','b'], ['a','d'], ['e','f'], ['g','h'], ['e','i']]
out = list(gen_take_first(inp))
print(out)
[['a', 'b'], ['e', 'f'], ['g', 'h']]

How to make a nested list in python

Suppose I have a 2 lists in my python script:
my_list = ['hat', 'bat']
other_list = ['A', 'B', 'C']
I want to iterate through other_list and create a nested list for 'bat's that adds '_' + other_list item to a the 'bat' and puts it in a nested list:
for item in other_list:
for thing in my_list:
if thing == 'bat':
print(thing + '_' + item)
My desired outcome would be new_list = ['hat',['bat_A', 'bat_B', 'bat_C']]
How would I achieve this?
I tried the below, but it produces this: ['hat', 'hat', 'hat', ['bat_A', 'bat_B', 'bat_C']]
new_list = []
extra = []
for item in other_list:
for thing in my_list:
if thing == 'bat':
extra.append(thing + '_' + item)
else:
new_list.append(thing)
new_list.append(extra)
Try this:
>>> my_list = ['hat', 'bat']
>>> other_list = ['A', 'B', 'C']
>>> new_list=[my_list[0], [f'{my_list[1]}_{e}' for e in other_list]]
>>> new_list
['hat', ['bat_A', 'bat_B', 'bat_C']]
If your question (which is a little unclear) is just about reacting to 'bat' with a different reaction, you can do this:
my_list = ['hat', 'bat','cat']
other_list = ['A', 'B', 'C']
new_list=[]
for e in my_list:
if e=='bat':
new_list.append([f'{e}_{x}' for x in other_list])
else:
new_list.append(e)
>>> new_list
['hat', ['bat_A', 'bat_B', 'bat_C'], 'cat']
Which can be reduced to:
>>> [[f'{e}_{x}' for x in other_list] if e=='bat' else e for e in my_list]
['hat', ['bat_A', 'bat_B', 'bat_C'], 'cat']
I think will work
my_list = ['hat', 'bat']
other = ['A', 'B' , 'C']
new_list = []
extra = []
for item in my_list:
if item == 'bat':
for char in other:
extra.append(item + '_' + char)
else:
new_list.append(item)
new_list.append(extra)
print(new_list)
OK, this is just my answer, but it seems to work. I think is clunky though, and I'm hoping for a better answer
my_list = ['hat', 'bat']
other_list = ['A', 'B', 'C']
new_list = []
extra = []
for item in other_list:
for thing in my_list:
if thing == 'bat':
extra.append(thing + '_' + item)
else:
if thing not in new_list:
new_list.append(thing)
new_list.append(extra)

The problem of using {}.fromkey(['k1','k2'],[]) and {'k1':[],'k2':[]}

list1 = [99,55]
dict1 = {'k1':[],'k2':[]}
for num in list1:
if num > 77:
dict1['k1'].append(num)
else:
dict1['k2'].append(num)
print(dict1)
{'k1':[99],'k2':[55]}
But when I replaced dict1 = {'k1':[],'k2':[]} to {}.fromkeys(['k1','k2'],[]) , the result became {'k1': [99, 55], 'k2': [99, 55]}
why this happens? I really have no idea.
This happens because you are passing the same list object to both keys. This is the same situation as when you create an alias for a variable:
a = []
b = a
a.append(55)
b.append(99)
print(b)
prints [55, 99] because it is the same list instance.
If you want to make it more concise from a list of keys to initialize with empty list, you can do this:
dict1 = {k: [] for k in ('k1', 'k2')}
This will create a new list instance for every key.
Alternatively, you can use defaultdict
from collections import defaultdict
list1 = [99,55]
dict1 = defaultdict(list)
for num in list1:
if num > 77:
dict1['k1'].append(num)
else:
dict1['k2'].append(num)
print(dict1)
Also works.
The fromKeys() can also be supplied with a mutable object as the default value.
if we append value in the original list, the append takes place in all the values of keys.
example:
list1 = ['a', 'b', 'c', 'd']
list2 = ['SALIO']
dict1 = dict.fromkeys(list1, list2)
print(dict1)
output:
{'a': ['SALIO'], 'b': ['SALIO'], 'c': ['SALIO'], 'd': ['SALIO']}
then you can use this:
list1 = ['k1', 'k2']
dict1 = {'k1':[],'k2':[]}
list2 =[99,55]
for num in list2:
if num > 77:
a = ['k1']
dict1 = dict.fromkeys(a, [num])
else:
b = ['k2']
dict2 = dict.fromkeys(b,[num] )
res = {**dict1, **dict2}
print(res)
output:
{'k1': [99], 'k2': [55]}
You can also use the python code to merge dict code:
this function:
def Merge(dict1, dict2):
return(dict2.update(dict1))
then:
print(Merge(dict1, dict2)) #This return None
print(dict2) # changes made in dict2

How to replace list element with string without double quotes?

I have a simple list like this:
list = ['A','B','C']
and to replace element #1 of l1 with this string:
str = "'W','T'"
I'm doing like this:
>>> list[1] = str
>>> list
['A', "'W','T'", 'C']
How can I do to replace list[1] values with str content without the double quotes? like this:
['A','W','T','C']
You can't insert it directly like that. You need to clean it first and convert it to a list and use slicing.
list1 = ['A','B','C']
str1 = "'W','T'"
new_list = [a.strip("'") for a in str1.split(",")]
list1 = list1[:1] + new_list + list1[2:]
print(list1) # ['A', 'W', 'T', 'C']
I also modified your variable names because list and str are reserved keywords.
You have to put the elements of the string into a list and then add the list elements to the desired position in your destination list.
list_ = ['A', 'B', 'C']
string = "'W','T'"
formatted = [letter for letter in string if letter.isalpha()]
i = 1 #index of element to replace
list_[i:(i + len(formatted))-1] = formatted
print(list_)
list[item] = str(list[item])
>>> mylist = [1,3,5]
>>> mylist[0] = str(mylist[0])
>>> mylist
['1', 3, 5]
>>>

find elements in lists using For Loop

keys = ['a','H','c','D','m','l']
values = ['a','c','H','D']
category = []
for index, i in enumerate(keys):
for j in values:
if j in i:
category.append(j)
break
if index == len(category):
category.append("other")
print(category)
My expected output is ['a', 'H', 'c', 'D', 'other', 'other']
But i am getting ['a', 'other', 'H', 'c', 'D', 'other']
EDIT: OP edited his question multiple times.
Python documentation break statement:
It terminates the nearest enclosing loop.
You break out of the outer loop using the "break" statement. The execution never even reaches the inner while loop.
Now.. To solve your problem of categorising strings:
xs = ['Am sleeping', 'He is walking','John is eating']
ys = ['walking','eating','sleeping']
categories = []
for x in xs:
for y in ys:
if y in x:
categories.append(y)
break
categories.append("other")
print(categories) # ['sleeping', 'walking', 'eating']
Iterate over both lists and check if any categories match. If they do append to the categories list and continue with the next string to categorise. If didn't find any matching category (defined by the count of matched categories being less than the current index (index is 0 based, so they are shifted by 1, which means == is less than in this case) then categorise as "other.

Resources