2

順列を生成するためのこの関数の慣用的なバージョンは、Rubyでどのように見えるのだろうかと思います。同じ結果が得られることは理解してい[1,2,3].permutation.to_aますが、Rubyの学習と、Rubyでこのような再帰的な問題に取り組む方法に興味があります。

def permutations(seq)
    if seq.empty? || seq.count == 1
        seq
    else
        seq.map { |x|
            permutations(seq.select { |e| e != x }).map { |p|
                if p.class == Fixnum
                    [x, p]
                else
                    p.unshift(x)
                end
            }
        }.flatten(1)
    end
end

ありがとう!

4

2 に答える 2

4
class Array
  def permutations
    return [self] if size < 2
    perm = []
    each { |e| (self - [e]).permutations.each { |p| perm << ([e] + p) } }
    perm
  end
end 

[1, 2, 3].permutations #=> [[1, 2, 3], [1, 3, 2], [2, 1, 3], [2, 3, 1], [3, 1, 2], [3, 2, 1]] 

出典: http: //blade.nagaokaut.ac.jp/cgi-bin/scat.rb/ruby/ruby-talk/32844

編集:モンキーパッチを避けるために、それをモジュールに入れてください:

module ArrayExtensions
  def permutations
    #snip
  end
end

Array.send :include, ArrayExtensions
于 2012-10-12T16:19:53.613 に答える
0

このような機能をコアクラスに直接追加することは、Ruby(特にRails)ではかなり一般的です。

このアプローチの代替案の1つは、別個の静的ユーティリティモジュールです。

module ArrayUtils
  def self.permute(array)
    return [array] if array.size < 2

    array.flat_map do |elem|
      permute(array - [elem]).map do |perm|
        ([elem] + perm)
      end
    end
  end
end

ArrayUtils.permute [1, 2, 3]
# => [[1, 2, 3], [1, 3, 2], [2, 1, 3], [2, 3, 1], [3, 1, 2], [3, 2, 1]]
于 2012-10-12T17:50:43.113 に答える