remove characters from the first items in list of lists - python

I have a nested list and in every list the first item is a string that ends with .abc. I would like to remove all the .abc characters from my nested list.
Here's what I have got:
x = [['car.abc', 1, 2], ['ship.abc', 3, 4]]
And I would like to my nested list to be the following:
x = [['car', 1, 2], ['ship', 3, 4]]
How can I achieve this?

Using a simple for loop.
x = [['car.abc', 1, 2], ['ship.abc', 3, 4]]
for i in x:
i[0] = i[0].rsplit(".", 1)[0]
print(x)

Using nested regular expressions and list comprehension:
>>> import re
>>> [[re.sub(r'.abc$', '', e) if isinstance(e, basestring) else e for e in l] for l in x]
[['car', 1, 2], ['ship', 3, 4]]
isinstance(e, basestring) checks whether e is a string (see this question).
For a string e, re.sub(r'.abc$', '', e) replaces the part you specified
Otherwise e is untouched
The preceding happens for any element e in a list l, for each l in x.

Check online demo
x = [['car.abc', 1, 2], ['ship.abc', 3, 4]]
new_x=[]
for lst in x:
temp_lst=[]
for item in lst:
if(str(item)[-4:] == '.abc'):
item = str(item)[:-4]
temp_lst.append(item)
new_x.append(temp_lst)
print(new_x)

Related

Python: how to remove single quote on first and last element of list

i have a list that goes like this ['1,2'] and i need to turn it into [1, 2]. Using int() won't work. Is there a way to add a single quote and then use int(), a way to remove a single quote or is there just a better way to do this?
here is the code that i am using
a_list = genres_selected.split()
map_object = map(int, a_list)
genres_selected_use = list(map_object)
genres_selected will always be different as it is being passed through ajax form
but here it is "1, 2"
I think you are looking to remove the string and convert it into an integer. Since the list has a string, you want to split the string using comma delimiter.
list_vals = ['1,2,3,4,5,6']
map_object = map(int, list_vals[0].split(','))
print (list(map_object))
The output of this will be:
[1, 2, 3, 4, 5, 6]
However, if your list has multiple strings of integers in single quotes, you can do:
my_list = ['1,2','3,4','5,6']
num_list = [[int(i) for i in num.split(',')] for num in my_list]
print (num_list)
The output of this will be:
[[1, 2], [3, 4], [5, 6]]
lst = ['1,2', '3,4,5']
new_list = []
for item in lst:
new_list.extend([int(num) for num in item.strip().split(',')])
print(new_list)
>>> [1, 2, 3, 4, 5]
One Liner Version
lst = ['1,2', '3,4,5']
print([int(item) for sublist in map(lambda item: item.split(','), lst) for item in sublist])
>>> [1, 2, 3, 4, 5]

convert nested list to int or str

I have the following list structure:
the_given_list = [[[1],[2],[3]],[[1],[2],[3]]]
Indeed len(the_given_list) returns 2.
I need to make the following list:
the_given_list = [[1,2,3],[1,2,3]]
How to do it?
[sum(x, []) for x in the_given_list]
Flatten the first-order element in the_given_list.
the_given_list = [sum(x, []) for x in the_given_list]
print(the_given_list)
To explain the above answer https://stackoverflow.com/a/57369395/1465553, this list
[[[1],[2],[3]],[[1],[2],[3]]]
can be seen as
[list1, list2]
and,
>> sum([[1],[2],[3]], [])
[1,2,3]
>>> sum([[1],[2],[3]], [5])
[5, 1, 2, 3]
Since the second argument to method sum defaults to 0, we need to explicitly pass empty list [] to it to overcome type mismatch (between int and list).
https://thepythonguru.com/python-builtin-functions/sum/
Use itertools.chain
In [15]: from itertools import chain
In [16]: [list(chain(*i)) for i in the_given_list]
Out[16]: [[1, 2, 3], [1, 2, 3]]
the_given_list = [ [ s[0] for s in f ] for f in the_given_list ]
Another solution:
the_given_list = [[[1],[2],[3]],[[1],[2],[3]]]
print([[j for sub in i for j in sub] for i in the_given_list])
Gives me:
[[1, 2, 3], [1, 2, 3]]
Check the original answer on list flattening:
https://stackoverflow.com/a/952952/5501407

python - Comparing two lists to see if one occurs in another consecutively

I've been trying to make a function that can take two lists of any size (say, list A and list B) and sees if list B occurs in list A, but consecutively and in the same order. If the above is true, it returns True, else it'll return False
e.g.
A:[9,0,**1,2,3,4,5,6,**7,8] and B:[1,2,3,4,5,6] is successful
A:[1,2,0,3,4,0,5,6,0] and B:[1,2,3,4,5,6] is unsuccessful.
A:[1,2,3,4,5,6] and B [6,5,3,2,1,4] fails because despite having the same
numbers, they aren't in the same order
I've tried doing this using nested loops so far and am a bit confused as to where to go
Just try this:
L1 = [9,0,1,2,3,4,5,6,7,8]
L2 = [1,2,3,4,5,6]
c = 0
w = 0
for a in range(len(L2)):
for b in range(w+1, len(L1)):
if L2[a] == L1[b]:
c = c+1
w = b
break
else:
c = 0
if c == len(L2):
print('yes')
break
Here you check if the element of l2 is in l1 and if so breaks the first loops remember where you left and of the next element of l2 is the same as the next element of l1 and so on.
And the last part is to check if this happened as much times as the length of l2. if so then you know that the statement is correct!
if your arrays are not huge and if you can find a way to map each element in your array to a string you can use:
list1 = [9,0,1,2,3,4,5,6,7,8]
list2 = [1,2,3,4,5,6]
if ''.join(str(e) for e in list2) in ''.join(str(e) for e in list1):
print 'true'
it just make two string from the lists and than use 'in' to find any accorence
Use any function
any(A[i:i+len(B)] == B for i in range(len(A) - len(B) + 1))
demo
i converted the entire list into a string and then found a substring of that string
the list when converted to a string it becomes
str(a)='[9,0,1,2,3,4,5,6,7,8]'
which when when we strip the string becomes
str(a).strip('[]')='9,0,1,2,3,4,5,6,7,8'
Now the problem just converted to
checking if there is a substring in the the string
so we can us the in operator to check the substring
The solution
a=[9,0,1,2,3,4,5,6,7,8]
b=[1,2,3,4,5,6]
print(str(b).strip('[]') in str(a).strip(']['))
testcase1
testcase2
Try this:
L1 = [9,2,1,2,0,4,5,6,7,8]
L2 = [1,2,3,4,5,6]
def sameorder(L1,L2):
for i in range(len(L1)-len(L2)+1):
if L1[i:len(L2)+i]==L2:
return True
return False
You can create sublists of a that can be analyzed:
def is_consecutive(a, b):
return any(all(c == d for c, d in zip(b, i)) for i in [a[e:e+len(b)] for e in range(len(a)-len(b))])
cases = [[[9, 0, 1, 2, 3, 4, 5, 6, 7, 8], [1, 2, 3, 4, 5, 6]], [[1, 2, 0, 3, 4, 0, 5, 6, 0], [1, 2, 3, 4, 5, 6]], [[1, 2, 3, 4, 5, 6], [6, 5, 3, 2, 1, 4]]]
final_cases = {"case_{}".format(i):is_consecutive(*a) for i, a in enumerate(cases, start=1)}
Output:
{'case_3': False, 'case_2': False, 'case_1': True}

Group repeated elements of a list

I am trying to create a function that receives a list and return another list with the repeated elements.
For example for the input A = [2,2,1,1,3,2] (the list is not sorted) and the function would return result = [[1,1], [2,2,2]]. The result doesn't need to be sorted.
I already did it in Wolfram Mathematica but now I have to translate it to python3, Mathematica has some functions like Select, Map and Split that makes it very simple without using long loops with a lot of instructions.
result = [[x] * A.count(x) for x in set(A) if A.count(x) > 1]
Simple approach:
def grpBySameConsecutiveItem(l):
rv= []
last = None
for elem in l:
if last == None:
last = [elem]
continue
if elem == last[0]:
last.append(elem)
continue
if len(last) > 1:
rv.append(last)
last = [elem]
return rv
print grpBySameConsecutiveItem([1,2,1,1,1,2,2,3,4,4,4,4,5,4])
Output:
[[1, 1, 1], [2, 2], [4, 4, 4, 4]]
You can sort your output afterwards if you want to have it sorted or sort your inputlist , then you wouldnt get consecutive identical numbers any longer though.
See this https://stackoverflow.com/a/4174955/7505395 for how to sort lists of lists depending on an index (just use 0) as all your inner lists are identical.
You could also use itertools - it hast things like TakeWhile - that looks much smarter if used
This will ignore consecutive ones, and just collect them all:
def grpByValue(lis):
d = {}
for key in lis:
if key in d:
d[key] += 1
else:
d[key] = 1
print(d)
rv = []
for k in d:
if (d[k]<2):
continue
rv.append([])
for n in range(0,d[k]):
rv[-1].append(k)
return rv
data = [1,2,1,1,1,2,2,3,4,4,4,4,5,4]
print grpByValue(data)
Output:
[[1, 1, 1, 1], [2, 2, 2], [4, 4, 4, 4, 4]]
You could do this with a list comprehension:
A = [1,1,1,2,2,3,3,3]
B = []
[B.append([n]*A.count(n)) for n in A if B.count([n]*A.count(n)) == 0]
outputs [[1,1,1],[2,2],[3,3,3]]
Or more pythonically:
A = [1,2,2,3,4,1,1,2,2,2,3,3,4,4,4]
B = []
for n in A:
if B.count([n]*A.count(n)) == 0:
B.append([n]*A.count(n))
outputs [[1,1,1],[2,2,2,2,2],[3,3,3],[4,4,4,4]]
Works with sorted or unsorted list, if you need to sort the list before hand you can do for n in sorted(A)
This is a job for Counter(). Iterating over each element, x, and checking A.count(x) has a O(N^2) complexity. Counter() will count how many times each element exists in your iterable in one pass and then you can generate your result by iterating over that dictionary.
>>> from collections import Counter
>>> A = [2,2,1,1,3,2]
>>> counts = Counter(A)
>>> result = [[key] * value for key, value in counts.items() if value > 1]
>>> result
[[2, 2, 2], [[1, 1]]

How can I remove all instances of an element from a list in Python? [duplicate]

This question already has answers here:
Remove all occurrences of a value from a list?
(26 answers)
Closed 7 years ago.
Lets say I have a list a:
a = [[1, 1], [2, 2], [1, 1], [3, 3], [1, 1]]
Is there a function that removes all instances of [1, 1]?
If you want to modify the list in-place,
a[:] = [x for x in a if x != [1, 1]]
Use a list comprehension:
[x for x in a if x != [1, 1]]
Google finds Delete all items in the list, which includes gems such as
from functools import partial
from operator import ne
a = filter(partial(ne, [1, 1]), a)
def remAll(L, item):
answer = []
for i in L:
if i!=item:
answer.append(i)
return answer
Here is an easier alternative to Alex Martelli's answer:
a = [x for x in a if x != [1,1]]
new_list = filter(lambda x: x != [1,1], a)
Or as a function:
def remove_all(element, list):
return filter(lambda x: x != element, list)
a = remove_all([1,1],a)
Or more general:
def remove_all(elements, list):
return filter(lambda x: x not in elements, list)
a = remove_all(([1,1],),a)
filter([1,1].__ne__,a)
pure python no modules version, or no list comp version ( simpler to understand ?)
>>> x = [1, 1, 1, 1, 1, 1, 2, 3, 2]
>>> for item in xrange(x.count(1)):
... x.remove(1)
...
>>>
>>> x
[2, 3, 2]
can be made into a def pretty easily also
def removeThis(li,this):
for item in xrange(li.count(this)):
li.remove(this)
return li

Categories