我需要调整一些3D数据的大小,例如2d数据的tf.image.resize_images
方法。
我在想我可以尝试在循环和交换轴上运行tf.image.resize_images
,但我认为必须有一个更简单的方法。简单的最近邻居应该没问题。
有什么想法吗?它并不理想,但我可以满足于数据只有0或1的情况,并使用类似的东西:
tf.where(boolMap, tf.fill(data_im*2, 0), tf.fill(data_im*2), 1)
但我不确定如何获得boolMap
。使用tf.while_loop
来覆盖所有值会大大降低性能吗?除非有某种自动循环并行化,否则我觉得它会在GPU上运行。
数据是一个大小为[batch_size, width, height, depth, 1]
提前致谢。
N.B输出尺寸应为:
[batch_size, width*scale, height*scale, depth*scale, 1]
我想出了这个:
def resize3D(self, input_layer, width_factor, height_factor, depth_factor):
shape = input_layer.shape
print(shape)
rsz1 = tf.image.resize_images(tf.reshape(input_layer, [shape[0], shape[1], shape[2], shape[3]*shape[4]]), [shape[1]*width_factor, shape[2]*height_factor])
rsz2 = tf.image.resize_images(tf.reshape(tf.transpose(tf.reshape(rsz1, [shape[0], shape[1]*width_factor, shape[2]*height_factor, shape[3], shape[4]]), [0, 3, 2, 1, 4]), [shape[0], shape[3], shape[2]*height_factor, shape[1]*width_factor*shape[4]]), [shape[3]*depth_factor, shape[2]*height_factor])
return tf.transpose(tf.reshape(rsz2, [shape[0], shape[3]*depth_factor, shape[2]*height_factor, shape[1]*width_factor, shape[4]]), [0, 3, 2, 1, 4])
转过来:
成:
我认为最近的邻居不应该有阶梯效应(我有意删除了颜色)。
Hars的回答是正确的,但我想知道如果有人能破解它,我的错了什么。
答案 0 :(得分:4)
我的方法是沿两个轴调整图像大小,在下面的代码中粘贴,我沿深度重新采样然后宽度
def resize_by_axis(image, dim_1, dim_2, ax, is_grayscale):
resized_list = []
if is_grayscale:
unstack_img_depth_list = [tf.expand_dims(x,2) for x in tf.unstack(image, axis = ax)]
for i in unstack_img_depth_list:
resized_list.append(tf.image.resize_images(i, [dim_1, dim_2],method=0))
stack_img = tf.squeeze(tf.stack(resized_list, axis=ax))
print(stack_img.get_shape())
else:
unstack_img_depth_list = tf.unstack(image, axis = ax)
for i in unstack_img_depth_list:
resized_list.append(tf.image.resize_images(i, [dim_1, dim_2],method=0))
stack_img = tf.stack(resized_list, axis=ax)
return stack_img
resized_along_depth = resize_by_axis(x,50,60,2, True)
resized_along_width = resize_by_axis(resized_along_depth,50,70,1,True)
其中x将是3维张量或灰度或RGB; resized_along_width是最终调整大小的张量。这里我们要将三维图像的大小调整为(50,60,70)
的尺寸答案 1 :(得分:3)
张量已经是4D,1D分配给' batch_size'和其他3D分配宽度,高度,深度。如果您希望处理3D图像并在此配置中批量生成它们
[batch_size, width, height, depth, 1]
然后使用挤压功能移除到不必要的最终尺寸,如下所示:
tf.squeeze(yourData, [4])
这将输出张量或形状
[batch_size, width, height, depth]
tensorflow会优雅使用的是什么。
<强>除了强>
如果你有方便的尺寸,并且想要使用tensorflow的重塑能力,你可能会这样:
reshapedData = tf.reshape(yourData, [batch_size, width, height, depth])
就我个人而言,我使用 squeeze 向下一个程序员声明你的代码只打算摆脱1号尺寸,而重塑我可以更多,并留下下一个开发者必须弄清楚你为什么要重塑。
更新以包含更改的第4维
您希望有时使用维度
[batch_size, width, height, depth, 1]
有时使用
[batch_size, width, height, depth, n]
没问题。它是相同的解决方案,但现在你不能使用 squeeze 而只是留下 reshape ,如下所示:
reshapedData = tf.reshape(yourData, [batch_size, width, height, depth*n])
这怎么可行?让我们想象深度是图像帧的数量, n 是颜色深度(RGB可能是3)。重塑将一个接一个地堆叠颜色框架。毫无疑问,你的张量流在输入后立即有一个卷积层。卷积层将像您的单色帧一样轻松处理您的彩色帧堆栈(尽管具有更强的计算能力和参数)。
并添加了缩放
好的,这是如何缩放图像,在调整大小后使用 tf.image.resize_images :
reshapedData = tf.image.resize_images( tf.reshape(yourData, [batch_size, width, height, depth*n]) , new_size )
其中size是2D张量,如果[new_height,new_width],或者在你的情况下 [width * scale,height * scale]
new_size = tf.constant( [ width * scale , height * scale ] )
然后回到原来的
如果在完成图像的所有调整之后,您希望它再次处于以下形状:[batch_size, width, height, depth, n]
,那么只需使用此代码
tf.reshape(yourData, [batch_size, width*scale, height*scale, depth,n])
最后添加地址缩放深度
这是我的解决方案:
我们想要重塑这个矩阵,并将其展开类似于如何在这样的numpy中扩展3d矩阵
a = np.array([[1, 2, 3, 4, 5, 6, 7, 8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,26,27],[1, 2,3, 4, 5, 6, 7, 8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25,26,27]])
print a.reshape([2,3,3,3])
a.reshape([54,1]).dot(np.ones([1,8])).reshape([2,3,3,3,2,2,2]).transpose([0,1,6,2,5,3,4]).reshape([2,6,6,6])
print a
这是张量流代码
isolate = tf.transpose(yourdata,[0,4,1,2,3]) # [batch_size,n,width,height,depth]
flatten_it_all = tf.reshape([batch_size * n * width * height * depth , 1]) # flatten it
expanded_it = flatten_it_all * tf.ones( [1,8] )
prepare_for_transpose = tf.reshape( expanded_it , [batch_size*n,width,height,depth,2,2,2] )
transpose_to_align_neighbors = tf.transpose( prepare_for_transpose, [0,1,6,2,5,3,4])
expand_it_all = tf.reshape( transpose_to_align_neighbors , [batch_size,n,width*2,height*2,depth*2] )
#### - removing this section because the requirements changed
# do a conv layer here to 'blend' neighbor values like:
# averager = tf.ones([2,2,2,1,1]) * 1. / 8.
# tf.nn.conf3d( expand_it_all , averager , padding="SAME")
# for n = 1. for n = 3, I'll leave it to you.
# then finally reorder and you are done
reorder_dimensions = tf.transpose(expand_it_all,[0,2,3,4,1]) # [batch_size,width*2,height*2,depth*2,n]