Python - Numpy 3D数组 - 连接问题

3

我有一个包含46个条目的txt文件,看起来像这样 -

2020-05-24T10:57:12.743606#[0.0, 0.0, 0.0653934553265572, 0.0, 1.0, 0.0]
2020-05-24T10:57:12.806380#[0.0, 0.0, 0.0, 0.0, 1.0, 0.0]
2020-05-24T10:57:12.869022#[0.0, 0.0, 0.0, 0.0, 1.0, 0.0]

第一个参数是所拍摄的相机图像的时间戳。对于每个时间戳,都有3个RGB图像。
我的目标是沿通道轴(axis = 2)将它们连接起来。图像尺寸为70x320x3,所需输出为46x70x320x9。
我需要等待所有3个图像被识别后,将它们附加到列表中并将其馈送到NumPy数组中。但我失败了,因为在连接之前,我得到的输出维度是46x138(来自附加的3张图像)x70x320x3 46x138x70x320x3。当使用axis =2或3实现连接时,连接无法正常工作。
从这个问题中,我该如何得到46x70x320x9
代码 -
with open("train.txt", 'r') as f:
    data = f.readlines()[:]
images = []
image_concat = []
labels = []
for row in data:
    for camera in ['center', 'left', 'right']:
        img_id, label = row.strip("\n").split("#")
        img_path = os.path.join(IMG_PATH, '{}-{}.jpg'.format(camera, img_id))
        image = cv2.imread(img_path)
        images.append(image)
        if camera == 'right':
            image_concat.append(images)

X_data = np.array(image_concat)
print(X_data.shape)

相关链接 -

需要帮助将两个3通道图像合并为6通道图像(Python)

numpy:沿第三维连接两个数组

numpy连接多个数组

numpy通过维度进行连接

请帮忙,任何帮助都将不胜感激。谢谢。

2个回答

3

这里是一个使用虚拟数据的实现

collect = []
for i in range(46):

    #create dummy arrays, simulate list of 3 RGB images
    a = [np.zeros((70,320,3)) for b in range(3)]
    # a[0].shape: (70,320,3) 

    #concatenate along axis 2
    b = np.concatenate(a, axis=2)
    # b.shape: (70,320,9)

    #create new axis in position zero
    b = b[np.newaxis, ...]
    # b.shape : (1,70,320,9)
    collect.append(b)

output = np.concatenate(collect, axis=0)

output.shape
(46, 70, 320, 9)

编辑:

# IIUC:
# left camera makes 70,320,3 at time t
# right camera makes 70,320,3 at time t
# center camera makes 70,320,3 at time t
# these need to be concatenated to 70,320,9
# if so, you can use a dictionary

#initialise dict
collected_images = {}
for timepoint, row in enumerate(data):
    #at every timepoint, initialise dict entry
    collected_images[timepoint] = []
    for camera in ['center', 'left', 'right']:
        image = cv2.imread('path/to/image')
        collected_images[timepoint].append(image)

# now you have all images in a dictionary
# to generate the array, you can

output = []
for key, val in collected_iamges.items():
    temp = np.concatenate(val, axis=2)
    output.append(temp[np.newaxis, ...])

output = np.concatenate(output, axis=0)

谢谢您将其分解。我能够理解新轴如何在我的情况下有所帮助。在我的情况下,当我读取文本文件时,我会得到所有行,这导致了所有138个文件路径。我很难将其缩小到每3行以进行第一次连接。我需要找出方法。 - Deepak
1
非常感谢。您的分解不仅帮助我学习,而且让我更好地理解了问题。我不得不做出一些改变。已完成。 - Deepak
抱歉再次打扰您。我将逻辑扩展到一个更大的数据集,包含110,000个时间戳和3倍于图像数量。脚本崩溃并显示“总线错误(core dumped)”消息。我没有看到内存或CPU使用率的急剧增加。但是,我认为使用字典会导致过多的持久内存。有其他解决此问题的方法吗? - Deepak
@Deepak 如果我理解正确的话,您想要创建一个形状为(110000,70,320,9)的数组。这个对象的大小为165 gb。我建议您改变策略,使用较小的数据包进行处理。您可以一次加载和处理较小的块。 - warped
更改了我的逻辑--使用列表代替字典。将一个包含3个图像的列表附加到一个新列表中,对其进行连接,然后将其附加到另一个列表中,并在每次迭代中删除这3个图像列表。解决了内存问题。 - Deepak

1
@warped的第一个回答之后,我发现文本文件中的输出列表是问题所在。它会一次性转储所有行。经过多次尝试,我最终使用了csv.reader,这让事情变得更加容易。之后只需扩展@warped的第二个答案,就可以完成任务了。
with open('train.txt', 'r') as f:
    lines = f.readlines()
    data = csv.reader(lines, delimiter = "#")
    for count, index in enumerate(data):
        img_id = index[0]
        label = [float(item) for item in index[1][1:-1].split(",")]

从这里开始的标签解决方案 -- Python - 将字符串列表转换为浮点数 - 方括号和小数点导致问题

基本上使用了答案。

这个链接帮助我选择csv阅读器 -- Python无法正确读取文本文件?


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接