这个挑战是关于卷积神经网络及其两个主要的构建块,即卷积层和池层。
为了简单起见,我们忽略了图像和中间张量的“深度”,只看宽度和高度。
在图像处理中,卷积层的工作方式类似于内核。它由内核宽度和高度以及内核模式(最小、中或最大)定义。min内核在整个内核与原始图像重叠的位置提取值。对于中间核,内核的中心放置在图像的每个像素上;对于最大核,则考虑任何像素与内核重叠的所有位置。
每个内核的定位产生一个像素,从而产生一个小于(min)、等于(mid)或大于(最大)输入图像的2D阵列。
Kernel (C is the center)
###
#C#
###
Image
*****
*****
*****
*****
*****
Min kernel convolution (results in 3x3)
###** **###
#C#** **#C#
###** ... **###
***** *****
***** *****
... ...
***** *****
***** *****
###** ... **###
#C#** **#C#
###** **###
Mid kernel convolution (results in 5x5)
### ###
#C#*** ***#C#
###*** ***###
***** ... *****
***** *****
***** *****
... ...
***** *****
***** *****
***** ... *****
###*** ***###
#C#*** ***#C#
### ###
Max kernel convolution (results in 7x7)
### ###
#C# #C#
###**** ****###
***** *****
***** ... *****
***** *****
***** *****
... ...
***** *****
***** *****
***** ... *****
***** *****
###**** ****###
#C# #C#
### ###
如果输入映像有IR
行和IC
列,而内核有KR
行和KC
列,则输出维度定义如下:
IR - KR + 1
行、IC - KC + 1
列;如果结果行或列为零或负,则无效IR
行、IC
列;如果KR
或KC
是偶数,则出错IR + KR - 1
行,IC + KC - 1
列池层由窗口的宽度和高度以及水平和垂直步幅大小(在任一方向一次移动的单位数)来定义。见下图:
3x3 window, 2x2 stride pooling on a 7x7 image
###**** **###** ****###
###**** **###** ****###
###**** **###** ****###
******* ******* *******
******* ******* *******
******* ******* *******
******* ******* *******
******* ******* *******
******* ******* *******
###**** **###** ****###
###**** **###** ****###
###**** **###** ****###
******* ******* *******
******* ******* *******
******* ******* *******
******* ******* *******
******* ******* *******
******* ******* *******
###**** **###** ****###
###**** **###** ****###
###**** **###** ****###
如果输入映像具有IR
行和IC
列,而池层具有WR
/WC
行/列和SH
/SV
水平/垂直步长的窗口,则输出维度定义如下:
(IR - WR)/SV + 1
,如果(IR - WR) % SV != 0
或WR < SV
出错(IC - WC)/SH + 1
,如果(IC - WC) % SH != 0
或WC < SV
出错卷积层和池层可以任意叠加,从而使前一层的输出成为下一层的输入。向整个堆栈提供输入图像的维数,并应依次计算每个中间图像的维数。如果在任何层没有发生错误,则层堆栈是有效的。最终的输出大小并不重要,只要它可以没有错误的计算。
以下堆栈是有效的:
Input image 25x25
1. Min Convolution 3x3 => Intermediate image 23x23
2. Pooling 3x3 with stride 2x2 => Intermediate image 11x11
3. Max Convolution 3x3 => Intermediate image 13x13
4. Max Convolution 4x4 => Intermediate image 16x16
5. Pooling 2x2 with stride 2x2 => Intermediate image 8x8
6. Min Convolution 5x5 => Intermediate image 4x4
7. Pooling 4x4 with stride 3x3 => Output image 1x1
以堆栈的任何连续子序列作为输入,从相应的(中间)图像开始,也是有效的。(例如,输入图像23x23
的步骤2、3、4、5)
对上述7层堆栈的下列任何修改都将导致无效堆栈:
4x4
或2x4
替换步骤2:在至少一维范围内,步长大于窗口mid
卷积代替步骤3:图像大小在第7步变得太小mid
卷积替换步骤4:具有均匀核维数的中间卷积是一个错误。9x5
或更大替换步骤6:内核不适合图像(IR-KR+1
为零或负,这是一个错误)给定输入维度和卷积/池层堆栈的描述,确定它是否是有效的配置,即不是错误。
堆栈的描述可以以合理的方式表示。
所有的数字(内核大小,窗口大小,步幅)都保证是正整数。
您可以通过遵循您的语言约定或分别为true/false选择两个不同的值来输出真实/错误。
适用标准的密码-高尔夫规则。以字节为单位的最短代码获胜。
发布于 2020-06-25 03:29:25
sεÐgiĀ«]vyн³Dp-Nè©*-yθ/®+ÐïÊyнÈ®_*y`‹«à~i0q]1
受@萤火虫241的答案的启发,所以一定要投他一票!
三个松散的投入:
[w,h]
[[r,c]]
是卷积层,[[r,c],[r,c]]
是池层。-1
为max;0
为mid;1
为min;2
为池层。在网上试试。(由于q
没有测试套件,但我手动检查了四个falsey示例。)
s # Swap to get the first two (implicit) inputs onto the stack,
# with the second input at the top
ε # Map over each layer:
Ð # Triplicate the layer
gi # If it's length is 1 (thus a convolutional layer):
Ā # Truthify both integers, so we have a pair of 1s: [1,1]
« # Merge it to the layer
] # Close the if-statement and map
v # Loop over each layer `y`, consisting of two pairs [kernel,stride]:
yн # Get the first pair (the kernel)
³ # Push the third input-list of modes
Dp- # Transform the 2s into 1s (by checking for prime, and subtracting)
Nè # Get the mode at the current loop-index
© # Store it in variable `®` (without popping)
* # Multiply this mode to the kernel-pair
- # Subtract each from the dimensions-pair
yθ # Get the last pair (the stride)
/ # Divide the dimension-pair by the stride-pair
®+ # And add the modified mode `®` to each
Ð # Triplicate the modified dimensions-pair
ï # Cast the values in the top copy to integers
Ê # Check if the top two pairs are NOT equal
# (1 if the dimension-pair contains decimal values; 0 if integers)
yн # Push the kernel again
È # Check for both values if they're even (1 if even; 0 if odd)
®_ # Check if `®` is 0 (1 if 0; 0 if not)
* # Multiply the checks
y` # Push the kernel-pair and stride-pair separated to the stack
‹ # Check if [kernel-row < stride-row, kernel-column < stride-column]
« # Merge the pairs of checks together
à # Check of any are truthy of this quartet by taking the maximum
~ # Check if either is truthy by taking the bitwise-OR
i # If this is truthy:
0 # Push a 0
q # And stop the program
# (after which this 0 is output implicitly as result)
] # Close the if-statement and loop
1 # And push a 1
# (which will be output implicitly if we didn't encountered the `q`#qcStackCode#)
发布于 2020-06-25 06:14:11
包含一个层列表;mode x y
用于卷积,_1 0 1
用于min mid max
,2x2矩阵wx wy ,: sx sy
用于池,x y
用于初始映像。如果它是有效的描述,则返回0,否则返回1。
_ e.&>(1(+_*[><.)@+(-{.)%(]*>:)/@])`((+_*1>])@+}.(]-~*+_*(2|[)+:|@]){.)@.(]3=#)~&.>/
(…)`(…)@.(]3=#)~&.>/
我们从右边折叠列表(最初的25 25
代表),并根据左长度(卷积3,池2),从两个函数中进行选择。每当我们遇到错误时,我们将行或列维度设置为无穷大。对于卷积,例如_1 3 3
(最小3x3):
((+_*1>])@+}.(]-~*+_*(2|[)+:|@]){.)
}.( ){. split into 3 3 and _1 as arguments
|@] mode != 0?
2|[ 3 3 even?
+: not-or, so 1 iff mode = 0 and dimension even
_* if this^ returns 1, convert it to infinity
*+ add to this dim * mode (_3 _3)
]-~ subtract the mode (_2 _2)
+ add to the image dimension (23 23)
(+_*1>]) if the dimensions are less than 1, add infinity
对于池,例如左侧为3 3,:2 2
,右侧为23 23
:
(1(+_*[><.)@+(-{.)%(]*>:)/@])
(]*>:)/@] multiple stride with (window greater/equal stride?)
(-{.)% (image - window)% mstride, is infinity iff mstride is 0
1 + add one
(+_*[><.) add infinity if flooring a dimensions changes it
最后,在应用每一层之后:
_ e.&> unbox and check if at least one dimension is infinity
https://codegolf.stackexchange.com/questions/206455
复制相似问题