Related
I have list of lists such as :
my_list_of_list=[['A','B','C','E'],['A','B','C','E','F'],['D','G','A'],['X','Z'],['D','M'],['B','G'],['X','Z']]
as you can see, the list 1 and 2 share the most elements (4). So, I keep a list within my_list_of_list only if the 4 shared elements (A,B,C or E) are present within that list.
Here I then save within the list_shared_number[], only the lists 1,2,3 and 6 since the other does not contain (A,B,C or E).
Expected output:
print(list_shared_number)
[0,1,2,5]
Probably sub optimal because I need to iterate 3 times over lists but it's the expect result:
from itertools import combinations
from functools import reduce
common_elements = [set(i).intersection(j)
for i, j in combinations(my_list_of_list, r=2)]
common_element = reduce(lambda i, j: i if len(i) >= len(j) else j, common_elements)
list_shared_number = [idx for idx, l in enumerate(my_list_of_list)
if common_element.intersection(l)]
print(list_shared_number)
# Output
[0, 1, 2, 5]
Alternative with 2 iterations:
common_element = {}
for i, j in combinations(my_list_of_list, r=2):
c = set(i).intersection(j)
common_element = c if len(c) > len(common_element) else common_element
list_shared_number = [idx for idx, l in enumerate(my_list_of_list)
if common_element.intersection(l)]
print(list_shared_number)
# Output
[0, 1, 2, 5]
You can find shared elements by using list comprehension. Checking if index 0 and index 1:
share = [x for x in my_list_of_list[0] if x in my_list_of_list[1]]
print(share)
Assume j is each item so [j for j in x if j in share] can find shared inner elements. if the length of this array is more than 0 so it should include in the output.
So final code is like this:
share = [x for x in my_list_of_list[0] if x in my_list_of_list[1]]
my_list = [i for i, x in enumerate(my_list_of_list) if len([j for j in x if j in share]) > 0]
print(my_list)
You can use itertools.combinations and set operations.
In the first line, you find the intersection that is the longest among pairs of lists. In the second line, you iterate over my_list_of_list to identify the lists that contain elements from the set you found in the first line.
from itertools import combinations
comparison = max(map(lambda x: (len(set(x[0]).intersection(x[1])), set(x[0]).intersection(x[1])), combinations(my_list_of_list, 2)))[1]
out = [i for i, lst in enumerate(my_list_of_list) if comparison - set(lst) != comparison]
Output:
[0, 1, 2, 5]
Oh boy, so mine is a bit messy, however I did not use any imports AND I included the initial "finding" of the two lists which have the most in common with one another. This can easily be optimised but it does do exactly what you wanted.
my_list_of_list=[['A','B','C','E'],['A','B','C','E','F'],['D','G','A'],['X','Z'],['D','M'],['B','G'],['X','Z']]
my_list_of_list = list(map(set,my_list_of_list))
mostIntersects = [0, (None,)]
for i, IndSet in enumerate(my_list_of_list):
for j in range(i+1,len(my_list_of_list)):
intersects = len(IndSet.intersection(my_list_of_list[j]))
if intersects > mostIntersects[0]: mostIntersects = [intersects, (i,j)]
FinalIntersection = set(my_list_of_list[mostIntersects[1][0]]).intersection(my_list_of_list[mostIntersects[1][1]])
skipIndexes = set(mostIntersects[1])
for i,sub_list in enumerate(my_list_of_list):
[skipIndexes.add(i) for char in sub_list
if i not in skipIndexes and char in FinalIntersection]
print(*map(list,(mostIntersects, FinalIntersection, skipIndexes)), sep = '\n')
The print provides this :
[4, (0, 1)]
['E', 'C', 'B', 'A']
[0, 1, 2, 5]
This works by first converting the lists to sets using the map function (it has to be turned back into a list so i can use len and iterate properly) I then intersect each list with the others in the list of lists and count how many elements are in each. Each time i find one with a larger number, i set mostIntersections equal to the len and the set indexes. Once i go through them all, i get the lists at the two indexes (0 and 1 in this case) and intersect them to give a list of elements [A,B,C,E] (var:finalIntersection). From there, i just iterate over all lists which are not already being used and just check if any of the elements are found in finalIntersection. If one is, the index of the list is appended to skipIndexes. This results in the final list of indexes {indices? idk} that you were after. Technically the result is a set, but to convert it back you can just use list({0,1,2,5}) which will give you the value you were after.
I have a list like this,
A = [[0.8922063, 0.26672425],
[0.34475611, 0.35976697],
[0.33253499, 0.18923898],
[0.66872466, 0.46248986],
[0.72823733, 0.10537784],
[0.40903598, 0.70639412],
[0.79926596, 0.90095583],
[0.67886544, 0.84573289],
[0.3641813, 0.64296743],
[0.07461196, 0.74290527]]
which is the combination of lists of list
and I have another list
p = [5,4,2]
I need to sum up elements of list A corresponding to P, i.e, the sum of the first 5 sub-list of A, then the sum of the next 4 (6th to 9th) sub-list and finally the sum of the last 2 sub-list.
Transform your list p into a list of the slices you want:
>>> q = [0,5,9,10]
You can do that this way:
>>> q = [sum(p[:i]) for i in range(len(p)+1)]
Then sum the slices of A:
>>> for i in range(len(q)-1):
listn = sum(sum(x) for x in A[q[i]:q[i+1]])
print(listn)
4.35005729
5.34739895
0.81751723
This function returns a list of sums from chunks in A by keeping track of our last sliced element (starting at 0) and incrementing the index to slice with the numbers in p.
def sum_sublists(list1 : list, list2 : list) -> list:
sums=[]
last_slice = 0
for chunk_size in list2:
next_slice = last_slice+chunk_size
sums.append(sum([sum(el) for el in list1[last_slice:next_slice]]))
last_slice = next_slice
return sums
if __name__ == '__main__':
p = [5,4,1]
A = [[0.8922063, 0.26672425],
[0.34475611, 0.35976697],
[0.33253499, 0.18923898],
[0.66872466, 0.46248986],
[0.72823733, 0.10537784],
[0.40903598, 0.70639412],
[0.79926596, 0.90095583],
[0.67886544, 0.84573289],
[0.3641813, 0.64296743],
[0.07461196, 0.74290527],
]
print(sum_sublists(A, p))
I want to multiply a list of list with a list using python 3 suppose that the list of list is of name L as follows:
L = [[45.909221207388235, 84.41069326628269], [80.6591435966521, 47.93257841035172]]
and the second list is:
S = [0.002, 0.001]
the multiplication should be: L[0][0]* S[0] and L[0][1]* S[0] then L[1][0]* S[1] and L[1][1]* S[1].
I tried the zip method :
[a*b for x,y in zip(S,L) for a,b in zip(x,y)]
But an error appears: zip argument 1 must support iteration.
the second trial was using map(lambda):
map(lambda x,y:x*y,L,S)
but the obtained results were wrong:
[9.181844241477647e-05, 0.00016882138653256538, 0.0001613182871933042, 9.586515682070343e-05]
the correct values are:
[0.09181844241477648, 0.1688213865325654, 0.0806591435966521, 0.047932578410351714]
You want to use zip, but not twice:
>>> L = [[45.909221207388235, 84.41069326628269], [80.6591435966521, 47.93257841035172]]
>>> S = [0.002, 0.001]
>>> [n*x for n, sub in zip(S, L) for x in sub]
[0.09181844241477648, 0.1688213865325654, 0.0806591435966521, 0.047932578410351714]
>>>
So, you want to pair up every number with every sublist, then multiply every number in the sublist by that main number.
Note, just in case you are using numpy (I don't think you are, and I don't think it would be reasonable to use numpy just for this), and S and L are numpy.ndarray objects, i.e.:
>>> S = np.array(S)
>>> L = np.array(L)
Then you probably just want:
>>> (S*L).ravel()
array([0.09181844, 0.08441069, 0.16131829, 0.04793258])
If I understand corresly you want to multiply each column in L by the corresponding value of S:
L = [[45.909221207388235, 84.41069326628269],
[80.6591435966521, 47.93257841035172]]
S = [0.002, 0.001]
R = [ [s*n for n in row] for s,row in zip(S,L) ]
output:
print(R)
[ [0.09181844241477648, 0.1688213865325654],
[0.0806591435966521, 0.047932578410351714]]
You should have given an example with a different number of rows than columns to make this clearer
I have a function that takes in any 2-d array and return a 2-d array (the same format as the array being implemented) but the values are squared.
i.e [[1,2],[3,4]] -----> [[1,4],[9,16]]
my code so far:
m0 = [[1,2],[3,4]]
empty_list = []
for x in m0:
for i in x:
empyt_list.append(x**2)
This gives me a 1-d array but how would i return a 2-d array as the imputed value?
You can make a recursive function to handle any depth of nested lists:
def SquareList(L):
if type(L) is list:
return [SquareList(x) for x in L]
else:
return L**2
Example:
> print(SquareList([1,[3],[2,[3]],4]))
[1, [9], [4, [9]], 16]
Working with an outer list
The point is that you will need an extra list outside to store the columns. So we can introduce temporary lists we build up and add as rows:
m0 = [[1,2],[3,4]]
result = []
for sublist in m0:
row = []
for item in sublist:
row.append(item**2)
result.append(row)
Notice that we here iterate over the items of the sublist.
Using list comprehension
We can however write this more elegantly with list comprehension
result = [[x*x for x in sublist] for sublist in m0]
Note: if you have to square a number x, it is usually more efficient to use x * x, then to write x ** 2.
Using numpy (for rectangular lists)
In case the list is rectangular (all sublists have the same length), we can use numpy instead:
from numpy import array
a0 = array(m0)
result = a0 ** 2
You can just do this by a list comprehension:
empty_list = [[m0[i][j]**2 for j in range(len(m0[i]))] for i in range(len(m0))]
Or like your Codestyle:
empty_list = m0
for i in range(len(m0)):
for j in range(len(m0[i])):
empty_list[i][j] = m0[i][j] ** 2
Your problem is that you never created a 2D-list and you just append the values on the created 1D-list.
I would like to know how to extract sub_arrayes from an array(which can be in different sizes). Therefore, by given an array I want a sum of sub array elements like:
Array = [1, 2, 3]
SubArray = [(1),(2),(3),(1,2),(2,3),(1,2,3)]
My question is, how to create such a sub array for an array with different size and how to XOR subArray elements as a final result in python.
I don't want to use numpy!
You could use:
sublist = []
for i in range(1, len(mylist)+1): # number of items in sublist
for j in range(len(mylist)-i+1): # index of sublist
sublist.append( tuple(mylist[j:j+i]) )
For the second problem (xor-ing all elements), you can use:
result = 0
for sub in sublist:
for e in sub:
result ^= e
However, if you don't need sublist after this, you can just do:
sublist = []
for i in range(1, len(mylist)+1): # number of items in sublist
for j in range(len(mylist)-i+1): # index of sublist
for e in mylist[j:j+i]:
result ^= e
This removes some redundancy.
You can use something like this:
itertools.chain(*(itertools.combinations(Array, r=r) for r in range(1, len(Array)+1)))