Вы не можете переопределить присваивание, потому что это оператор, а не метод. Но если ваш класс AllYourCode наследуется от Array, ваш пример будет работать.
Когда Ruby встречает назначение, он смотрит на правую сторону и, если существует более одного значения, он собирает их в массив. Затем он смотрит на левую сторону. Если там есть одно значение lvalue, ему присваивается массив.
def foo
return "a", "b", "c" # three rvalues
end
x = foo # => x == ["a", "b", "c"]
Если существует более одного l-значения (точнее, если он видит запятую), он последовательно присваивает r-значения и отбрасывает дополнительные.
x, y, z = foo # => x == "a", y == "b", z == "c"
x, y = foo # => x == "a", y == "b"
x, = foo # => x == "a"
Вы можете выполнять параллельное присваивание, если массив также возвращается, как вы обнаружили.
def bar
["a", "b", "c"]
end
x = bar # => x == ["a", "b", "c"]
x, y, z = bar # => x == "a", y == "b", z == "c"
x, y = bar # => x == "a", y == "b"
x, = bar # => x == "a"
Итак, в вашем примере, если rb является массивом или наследуется от массива, x и y будут назначены его первые 2 значения.