简体   繁体   中英

create a 2D array from a 1D array and a Boolean array in python

Hello I'm trying to create a 2d array from these array

A=[5, 7, 1, -3, 0, 2, 2, 7, 10, 11, -1, 8, 5, 18, 9]

B=[False, False, True, True, True, False, True, True, False, False, False, True, False, True, True]

I hope to get a matrix like this

C= [[1, -3, 0],
    [2, 7],
    [8],
    [18,9]]

that is, every time that change the array B from False to True, create a new row with consecutive True values.

please someone can help me

Regular integer NumPy arrays cannot have a jagged shape, eg for a 2d array, each row must have the same numbers of columns. But you can create a list of arrays via np.split :

lst_of_array = np.split(A, np.where(np.diff(B) == 1)[0]+1)[{0:1,1:0}[B[0]]::2]

# [array([ 1, -3,  0]),
#  array([2, 7]),
#  array([8]),
#  array([18,  9])]

Or for a list of lists:

from operator import methodcaller

lst_of_lst = list(map(methodcaller('tolist'), lst_of_array))

# [[1, -3, 0],
#  [2, 7],
#  [8],
#  [18, 9]]

Here's a method using a generator. No real reason to use a generator rather than a function actually, just what I first jumped to.

def splitter(A, B):
    sublist = []
    for item, check in zip(A, B):
        if not check:
            if sublist:
                yield sublist 
                sublist = []
        else:
            sublist.append(item)
    if sublist:
        yield sublist

A = [5, 7, 1, -3, 0, 2, 2, 7, 10, 11, -1, 8, 5, 18, 9]
B = [False, False, True, True, True, False, True, True, False, False, False, True, False, True, True]

list(splitter(A, B))

Output:

[[1, -3, 0], [2, 7], [8], [18, 9]]

This algorithm loops through A , accumulates consecutive true A values into D , until a false A value has been encountered, and only adds D to C if it has accumulated any true values in it. Finally, on the last loop through it appends D to C , again, if D has any values.

C = []
D = []
for i in range(len(A)):
    if B[i]:
        D.append(A[i])
    elif len(D):
        C.append(D)
        D = []
    if i == len(A)-1 and len(D):
        C.append(D)
from itertools import groupby, ifilter, izip
from operator import itemgetter

get_0 = itemgetter(0)

A=[5, 7, 1, -3, 0, 2, 2, 7, 10, 11, -1, 8, 5, 18, 9]
B=[False, False, True, True, True, False, True, True, False, False, False, True, False, True, True]

list((list((vv for _, vv in v))
    for _, v in
       ifilter(get_0, groupby(izip(B,A), get_0))))

Result:

[[1, -3, 0], [2, 7], [8], [18, 9]]

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM