问题描述
R,Python,Lua,Java,Matlab或任何编程语言中是否有任何函数可以通过删除全零来将3D input_array的大小从c(6,6,6)减小到c(4,4,4)矩阵在3维的外围?
## Create an empty array with all zeros
input_array <- array(data = c(0), dim = c(6, 6, 6))
## Populate the central locations of the array with 1
input_array[, ,2:5] <- matrix(c(0, 0, 0, 0, 0, 0,
0, 1, 1, 1, 1, 0,
0, 1, 1, 1, 1, 0,
0, 1, 1, 1, 1, 0,
0, 1, 1, 1, 1, 0,
0, 0, 0, 0, 0, 0),
nrow = 6, ncol = 6)
## Show the input_array
input_array
## The target output
output_array <- array(data = c(1), dim = c(4, 4, 4))
因此,换句话说,我正在寻找一个将input_array用作输入并将output_array用作输出的函数。 我想在整个转换过程中保持阵列的3D性质。 我要研究的原因是,我有非常大的3D数组,外围有很多零,并且通过从三个维度中删除全零矩阵,我可以实现这些数组大小的显着减少,因此允许以提高处理效率。
如果那里没有函数,那么编写一个新函数以完成此任务的逻辑是什么? 如果您有任何可分享的内容,请使用您喜欢的任何语言,非常感谢您提供任何反馈或帮助。
1楼
借助abind
包,您可以在R中做得相当好,这对于处理数组非常方便:
abind::asub(input_array, # take this and subset
lapply(1:3, function(d){ # iterate over its dimensions
apply(input_array != 0, d, any) # look for any non-zero elements
}))
## , , 1
##
## [,1] [,2] [,3] [,4]
## [1,] 1 1 1 1
## [2,] 1 1 1 1
## [3,] 1 1 1 1
## [4,] 1 1 1 1
##
## , , 2
##
## [,1] [,2] [,3] [,4]
## [1,] 1 1 1 1
## [2,] 1 1 1 1
## [3,] 1 1 1 1
## [4,] 1 1 1 1
##
## , , 3
##
## [,1] [,2] [,3] [,4]
## [1,] 1 1 1 1
## [2,] 1 1 1 1
## [3,] 1 1 1 1
## [4,] 1 1 1 1
##
## , , 4
##
## [,1] [,2] [,3] [,4]
## [1,] 1 1 1 1
## [2,] 1 1 1 1
## [3,] 1 1 1 1
## [4,] 1 1 1 1
2楼
感谢所有分享想法或引用其他类似文章的人。 我通过您的答案达到了这一点:
## Create an empty array with all zeros
input_array <- array(data = c(0), dim = c(6, 6, 6))
## Populate the central locations of the array with 1
input_array[, ,2:5] <- matrix(c(0, 0, 0, 0, 0, 0,
0, 1, 1, 1, 1, 0,
0, 1, 1, 1, 1, 0,
0, 1, 1, 1, 1, 0,
0, 1, 1, 1, 1, 0,
0, 0, 0, 0, 0, 0),
nrow = 6, ncol = 6)
## Show the input_array
input_array
## The target output
(output_array <- input_array[apply(input_array != 0, 3, any),
apply(input_array != 0, 2, any),
apply(input_array != 0, 1, any)])
我没有用不同的输入进行测试,因此可能需要对不同的输入进行进一步的测试。
3楼
这是一个选项( python
/ numpy
):
xcrit = np.where(np.any(input, axis=(0,1)))[0]
ycrit = np.where(np.any(input, axis=(0,2)))[0]
zcrit = np.where(np.any(input, axis=(1,2)))[0]
output = input[zcrit[0]:zcrit[-1]+1,ycrit[0]:ycrit[-1]+1,xcrit[0]:xcrit[-1]+1]
说明如果沿着传递的维度至少一个单元格为True,则np.any
返回True。
它返回一个形状类似于其余维度的布尔数组
np.where
查找其参数的True单元的索引。
在此示例中,我们使用它来查找沿每个坐标的第一个和最后一个非零切片的索引
样品运行:
>>> input = np.zeros((6,6,6))
>>> input[1:-2,1:-2,2:-1] = 1
>>> xcrit = np.where(np.any(input, axis=(0,1)))[0]
>>> ycrit = np.where(np.any(input, axis=(0,2)))[0]
>>> zcrit = np.where(np.any(input, axis=(1,2)))[0]
>>> output = input[zcrit[0]:zcrit[-1]+1,ycrit[0]:ycrit[-1]+1,xcrit[0]:xcrit[-1]+1]
>>> # verify
... input.sum(), output.sum(), output.size
(27.0, 27.0, 27)