user2469227
user2469227

Reputation:

Method changes a parameter array's value, unless the parameter is set to nil?

Here is a method I've been testing in the rails console.

def self.increment_index_array(index_array, sizes_array, last_index)
    index_array[last_index] += 1
    for i in (last_index).downto(0)
        if index_array[i] == sizes_array[i]
            if i == 0
                index_array = nil
                return index_array
            end 
            index_array[i] = 0
            index_array[i-1] += 1
        else
            break
        end
    end
    return index_array
end

I've been defining an index_array variable on the console and passing it to the method. The method is destructive on the index_array variable. Calling the method returns the incremented array, but also changes the variable value in the scope outside of the method (the console), which is desired. However, when I set the array to nil inside the method this change isn't reflected in the exterior scope. Why is this? Is there a way to make the variable nil in the exterior scope?

An example console session:

1.9.1 :191 > index = [64, 2, 3]
 => [64, 2, 3] 
1.9.1 :192 > sizes = [65, 3, 5]
 => [65, 3, 5]  
1.9.1 :193 > increment_index_array(index, sizes, 2)
 => [64, 2, 4] 
1.9.1 :194 > index
 => [64, 2, 4] 
1.9.1 :195 > increment_index_array(index, sizes, 2)
 => nil 
1.9.1 :196 > index
 => [65, 0, 0] 

Upvotes: 1

Views: 198

Answers (1)

Explosion Pills
Explosion Pills

Reputation: 191789

Ruby is a pass-by-value "everything is an object" language. Arrays are objects. When you use an array as an argument to a function, you are actually passing the reference to that array, which is mutable.

When performing an assignment, you are actually creating another reference and storing the value of that reference in the given scope.

If you want to change the type of the argument, you will have to do the assignment in the calling scope. Ruby has no symbol table alias functionality.

Upvotes: 1

Related Questions