这是我的阵列:
[[0,0,0,0],
[0,1,0,0],
[0,0,0,1],
[0,0,0,0]]
我希望“1”的上方,下方,右侧和左侧的“0”单元格也可以变为1。
预期输出为:
0100
1111
0111
0001
然而,我的代码:
class Image
def initialize(image)
@image = image
end
def output_image
@image.map do |image|
puts image.join('')
end
end
def blur
find_ones.each do |x, y|
blur_cell x, y
end
end
def find_ones
ones = []
@image.each_with_index do |row, y|
row.each_with_index do |cell, x|
ones << [x, y] if cell == 1
end
end
ones
end
def blur_cell(x, y)
write_cell x + 1, y, 1
write_cell x - 1, y, 1
write_cell x, y + 1, 1
write_cell x, y - 1, 1
end
def write_cell(x, y, value)
return nil unless y > 0 && y < @image.length
return nil unless x > 0 && x < @image[0].length
@image[y][x] = value
end
end
image = Image.new([
[0, 0, 0, 0],
[0, 1, 0, 0],
[0, 0, 0, 1],
[0, 0, 0, 0]
])
image.blur
image.output_image
我收到了这个输出:
0000
0111
0111
0001
任何帮助指出我的错误在哪里或任何有关如何解决它的建议将不胜感激:)
答案 0 :(得分:2)
您的代码中的错误
您的代码有一些小错误。以下是更正后的代码。将它与原始代码逐行进行比较,您将看到错误以及我如何修复它们。我也做了一些简化。
class Image
def initialize(image)
@image = image
end
def output_image
@image.map do |image|
puts image.join('')
end
end
def blur
find_ones.each do |x, y|
blur_cell x, y
end
end
def find_ones
ones = []
@image.each_with_index do |row, x|
row.each_with_index do |cell, y|
ones << [x, y] if cell == 1
end
end
ones
end
def blur_cell(x, y)
write_cell x + 1, y
write_cell x - 1, y
write_cell x, y + 1
write_cell x, y - 1
end
def write_cell(x, y)
return unless y >= 0 && y < @image.length
return unless x >= 0 && x < @image[0].length
@image[x][y] = 1 # was reversed
end
end
image = Image.new([
[0, 0, 0, 0],
[0, 1, 0, 0],
[0, 0, 0, 1],
[0, 0, 0, 0]
])
image.blur
image.output_image
#=> 0100
# 1111
# 0111
# 0001
建议的替代方案
这是另一种方法。
def convert(arr)
return [] if arr.empty?
nbr_rows = arr.size
nbr_cols = arr.first.size
a = container(arr)
(1..nbr_rows).
each_with_object(Array.new(nbr_rows) { Array.new(nbr_cols) }) { |i,b|
(1..nbr_cols).each { |j|
b[i-1][j-1] = [a[i][j], a[i][j-1], a[i][j+1], a[i-1][j], a[i+1][j]].max } }
end
def container(arr)
nbr_rows = arr.size
nbr_cols = arr.first.size
Array.new(nbr_rows+2) { |i|
Array.new(nbr_cols+2) { |j| (i.zero? || i==nbr_rows+1 || j.zero? ||
j==nbr_cols+1) ? 0 : arr[i-1][j-1] } }
end
示例强>
arr = [
[0, 0, 0, 0],
[0, 1, 0, 0],
[0, 0, 0, 1],
[0, 0, 0, 0]
]
convert arr
#=> [[0, 1, 0, 0],
# [1, 1, 1, 1],
# [0, 1, 1, 1],
# [0, 0, 0, 1]]
<强>解释强>
首先观察如果上,下,左或右的元素等于1,则将等于0的元素设置为1.对于不在第一行或最后一行或第一列或最后一列中的元素,计算很简单。处理周边元素的一种方法是构造第二个数组,该数组以原始数组开始,并在前后添加零行,并在左右添加零行。然后对除周边行和列之外的所有元素进行计算。最后,第一行和最后一行以及第一列和最后一列被剥离。这就是我所做的,
示例中使用的数组的步骤如下。首先考虑方法container
。
nbr_rows = arr.size
#=> 4
nbr_cols = arr.first.size
#=> 4
Array.new(nbr_rows+2) { |i|
Array.new(nbr_cols+2) { |j| (i.zero? || i==nbr_rows+1 || j.zero? ||
j==nbr_cols+1) ? 0 : arr[i-1][j-1] } }
#=> Array.new(6) { |i|
# Array.new(6) { |j| (i.zero? || i==5 || j.zero? ||
# j==5) ? 0 : arr[i-1][j-1] } }
#=> [[0, 0, 0, 0, 0, 0],
# [0, 0, 0, 0, 0, 0],
# [0, 0, 1, 0, 0, 0],
# [0, 0, 0, 0, 1, 0],
# [0, 0, 0, 0, 0, 0],
# [0, 0, 0, 0, 0, 0]]
请注意,此数组arr
夹在两行零和两列零之间。
现在让我们逐步完成convert
。
arr.empty?
#=> false, so we do not return []
nbr_rows = arr.size
#=> 4
nbr_cols = arr.first.size
#=> 4
a = container(arr)
#=> [[0, 0, 0, 0, 0, 0],
# [0, 0, 0, 0, 0, 0],
# [0, 0, 1, 0, 0, 0],
# [0, 0, 0, 0, 1, 0],
# [0, 0, 0, 0, 0, 0],
# [0, 0, 0, 0, 0, 0]]
(1..nbr_rows).each_with_object(Array.new(nbr_rows) { Array.new(nbr_cols) }) { |i,b|
(1..nbr_cols).each { |j|
b[i-1][j-1] = [a[i][j], a[i][j-1], a[i][j+1], a[i-1][j], a[i+1][j]].max } }
#=> (1..4).each_with_object(Array.new(4) { [0,0,0,0] }) { |i,b|
# (1..4).each { |j|
# b[i-1][j-1] = [a[i][j], a[i][j-1], a[i][j+1], a[i-1][j], a[i+1][j]].max } }
#=> [[0, 1, 0, 0],
# [1, 1, 1, 1],
# [0, 1, 1, 1],
# [0, 0, 0, 1]]
对于不熟悉Enumerable#each_with_object的读者,最后一个表达式实际上与以下三行相同。
b = Array.new(nbr_rows) { Array.new(nbr_cols) }
(1..nbr_rows).each { |i|
(1..nbr_cols).each { |j|
b[i-1][j-1] = [a[i][j], a[i][j-1], a[i][j+1], a[i-1][j], a[i+1][j]].max } }
b
答案 1 :(得分:1)
对于Ruby解决方案,请参阅@ CarySwoveland的答案。
由于您的课程名为blur_cell
且您的方法名称为convert matrix.png -morphology Dilate Diamond dilated_matrix.png
,因此您可能需要检查Image Magick和MiniMagick。
您正在寻找的转化称为"diamond dilation"。
使用ImageMagick,它很简单:
.pbm
转换
到
要将矩阵转换为位图,反之亦然,您可以使用 这个gem可以读取和写入{{1}}个文件。