I don't quite understand how to "initialize a multidimensional array to equal 1" as the initial for loops seem to suggest here. I haven't learned to properly read pseudocode, and I don't fully understand how this program works.
function countRoutes(m,n)
grid ← array[m + 1][n + 1]
for i = 0 to m do
grid[i][0] ← 1
end for
for j = 0 to n do
grid[0][j] ← 1
end for
for i = 1 to m do
for j = 1 to n do
grid[i][j] ← grid[i − 1][j] + grid[i][j − 1]
end for
end for
return grid[m][n]
end function
Thanks for your help!
This isn't hard to translate.. Ruby uses
=instead of left arrow for assignment, anddefinstead offunctionto define a subroutine (which it calls a method instead of a function), but that's about it. Let's go through it.That's beginning a function definition. In Ruby we use a method instead, and the keyword to define such a thing is
def. It's also convention in Ruby to use snake_case for multiword names instead of camelCase:Now to create the grid:
Ruby arrays are dynamic, so you don't normally need to specify the size at creation time. But that also means you don't get initialization or two-dimensionality for free. So what we have to do here is create an array of m+1 arrays, each of which can be empty (we don't need to specify that the sub-arrays need to hold n+1 items). Ruby's Array constructor has a way to do just that:
Now the initialization. Ruby technically has
forloops, but nobody uses them. Instead, we use iterator methods. For counting loops, there's a method on integers calledtimes. But the pseudocode counts from0throughminclusive;timesalso starts at0, but only counts up to one less than the invocant (so that way when you call3.times, the loop really does execute "three times", not four). In this case, that means to get the behavior of the pseudocode, we need to calltimesonm+1instead ofm:As an aside, we could also have done that part of the initialization inside the original array creation:
Anyway, the second loop, which would be more awkward to incorporate into the original creation, works the same as the first. Ruby will happily extend an array to assign to not-yet-existent elements, so the fact that we didn't initialize the subarrays is not a problem:
For the nested loops, the pseudocode is no longer counting from 0, but from 1. Counting from 1 through m is the same number of loop iterations as counting from 0 through m-1, so the simplest approach is to let
timesuse its natural values, but adjust the indexes in the assignment statement inside the loop. That is, where the pseudocode starts countingifrom 1 and referencesi-1andi, the Ruby code starts countingifrom 0 and referencesiandi+1instead.And the
returnstatement works the same, although in Ruby you can leave it off:Putting it all together, you get this: