Сохраняется ли порядок в массивах после пересечения?

Когда я делаю пересечение двух массивов, есть ли гарантия, что результирующий порядок основан на порядке первого массива?

Например, если у меня есть

a = [1,2,3]
b = [3,2,1]

мог a & b вернуть [3,2,1], вместо [1,2,3] (что я и ожидал)?

Я не могу найти ничего, касающегося этого, ни в документации RDoc, ни в кирке Array.

RubySpec имеет спецификацию, согласно которой он создает массив с элементами в порядке их первого столкновения, но должен ли я считать, что YARV Ruby будет соблюдать эту спецификацию?

3 ответа

Решение

Похоже, это гарантированная функция. Они обновили описание RDoc в ревизии 39415. Это должно быть отражено когда-нибудь.

В документации нет гарантии, но пересечение следует за порядком левого набора.

Источник показывает, что массив a устанавливает порядок:

...
for (i=0; i<RARRAY_LEN(ary1); i++) {
    vv = (st_data_t)(v = rb_ary_elt(ary1, i));
    if (st_delete(RHASH_TBL(hash), &vv, 0)) {
        rb_ary_push(ary3, v);
    }
}
...

Это просто проверить:

a = [1,2,3]
b = [3,2,1]

a.size.times do
    puts "a = #{ a.join(',') }\ta & b = #{ (a & b).join(',') }\tb & a = #{ (b & a).join(',') }"
  a.rotate! 
end

Какие выводы:

a = 1,2,3 a & b = 1,2,3 b & a = 3,2,1
a = 2,3,1 a & b = 2,3,1 b & a = 3,2,1
a = 3,1,2 a & b = 3,1,2 b & a = 3,2,1

Это использует Ruby 1.9.3-p374

YARV является официальным интерпретатором Ruby начиная с версии 1.9, поэтому я полагаю, что он соблюдает эту спецификацию. И кстати, RubySpec был создан как исполняемая спецификация языка, позволяя разработчикам создавать свои собственные интерпретаторы, которые соответствуют этой спецификации, и я считаю, что YARV был создан с учетом этого в RubySpec.

Другие вопросы по тегам