This is the exercise:
*Write a maximum_sequences function that receives two positive integers n and k and a list L1 of integers having length n * k and returns a list L2 of length k constructed as follows:
- we consider the n non-overlapping sub-lists of k elements in L1; -element L2 [j] contains the maximum of the elements found in position j in the sub-lists. Example: If n = 4, k = 3 and L1 = [7, 4, 7, 3, 6, 8, 9, 1, 5, 6, 2, 5], then: -the non-overlapping sublists of 3 elements in L1 are [7, 4, 7], [3, 6, 8], [9, 1, 5] and [6, 2, 5];
- L2 [0] = 9 because the elements in position 0 in the sub-lists are 7, 3, 9 and 6;
- L2 [1] = 6 because the elements in position 1 in the sub-lists are 4, 6, 1 and 2;
- L2 [2] = 8 because the elements in position 2 in the sub-lists are 7, 8, 5 and 5.*
Im stuck here:
def verify_list(n,k,Ll):
if len(Ll) != n*k:
raise SystemError
else:
return Ll
def max_sequenze(n,k,L1):
x = verify_list(n,k,L1)
sub_liste = []
l2 = []
for i in range(0, len(x),k):
sub_liste.append(x[i:i k])
How you can see i created the sub-arrays and the len check, but I have no idea how to build the L2 array (without Numpy). tnx
CodePudding user response:
For inputs
n = 4
k = 3
L1 = [7, 4, 7, 3, 6, 8, 9, 1, 5, 6, 2, 5]
We have two sub tasks: (A) splitting L1
into n
chunks of k
elements and (B) constructing L2, i.e. finding the maximum value for each index 0 to k -1
.
First we split L1
. We can define a slices
function that first asserts that we can indeed slice L1
into n
chunks of k
elements and then carries out the slicing. Notice that we yield every "slice", i.e. every sub list.
def slices(lst, n, k):
assert n*k == len(lst), "Misaligned dimensions!"
for i in range(0, n * k, k):
yield lst[i:i k]
Since we are using the yield
keyword, slices
will return a generator object. This is a very good practice and can often save one a lot of memory. The * operator is then used to unpack elements from the object. In this particular case, we unpack them into a list that we call subs
.
subs = [*slices(L1, n=4, k=3)]
# [7, 4, 7], [3, 6, 8], [9, 1, 5] [6, 2, 5]
Great, now we have our sub lists. Next, we can use the *
operator again to unpack the elements in subs
into the zip
function. The zip
functions joins multiple iterables (in our case, our sub lists) together index-wise, such that, in our case we get [(7, 3, 9, 6), (4, 6, 1, 2), (7, 8, 5, 5)]
. With this we can easily write a list comprehension that finds the max of each of these sub lists, which it the objective of task B.
L2 = [max(i) for i in zip(*subs)]
# [9, 6, 8]
Defining the subs
variable is just done for verbosity. We could easily unpack the object obtained from slices
directly into the zip
function like so.
L2 = [max(i) for i in zip(*slices(L1, n=n, k=k))]
# [9, 6, 8]
CodePudding user response:
The building of L2 can be done using another for loop. Loop through each index of a sublist, and find the maximum of all the elements at that index in all the sublists.
Something that will help here is the construction of an array for each of the sub_liste[i] elements that are being considered.
In the case where the first element of each sublist is considered, this can be done using this:
[a[0] for a in sub_liste]
Thereby building L2 can be done as shown:
for i in range(k):
l2.append(max([a[i] for a in sub_liste]))
CodePudding user response:
Since L2 is the maximum of the numbers in a particular index of the sub-lists, first iterate through 0 to k, so as to get the index and then for each of these iteration, go through the sub-lists and get the corresponding values and store them in a temporary list and append the maximum of that temporary list to L2... Like this
L2 = []
for i in range(k):
temp = []
for a in sub_res:
temp.append(a[i])
L2.append(max(temp))
Now using list comprehension, it can by shortened like this...
L2 = [max(a[i] for a in sub_res) for i in range(k)]