たとえば、3から23までの範囲で、4ずつ増えていく数列の配列を作りたいとする。 数学的にいうと初項3、公差4の数列を23になるまで作りたい こんな感じ。(最後のやつがいいたいくて書いたブログです)
[3, 7, 11, 15, 19, 23]
やり方を色々考えてみる。 環境はRuby3.1です。
Enumerable#selectで絞る
パッと思いつくものはselect
メソッドを使って絞り込むというもの。3, 7, 11, ... は4で割って3余る数の集合とみなせるので以下のようにできる。
(3..23).select { _1 % 4 == 3 }
Enumerable#mapで頑張る
(0..5).map { 4 * _1 + 3 }
一般項を求めてmapで変換するけど、これは少し苦しいなー。なぜ0から5とわかるんだと言われたら逆算してるので、、、と答えるしかない。 selectで絞るという方法もあるけど、、、微妙ですね。ボツ。
Enumerator::ArithmeticSequence クラスを使う
僕も初めて知ったんですが、Enumerator::ArithmeticSequence
なる等差数列を扱うクラスがあるみたい。
クラス名長すぎやしませんかね?笑
るりま:https://docs.ruby-lang.org/ja/latest/class/Enumerator=3a=3aArithmeticSequence.html
等差数列オブジェクトを作成するにはstepメソッドを使う
等差数列オブジェクトの生成 as = 3.step(by: 4, to: 23) => (3.step(by: 4, to: 23)) as.class => Enumerator::ArithmeticSequence as.to_a => [3, 7, 11, 15, 19, 23] # こうも書ける as = 3.step(23, by: 4)
Enumerableモジュールを継承(インクルード)しているのでループ処理をするだけならto_a
は不要です。
%
を使って短く記述することも可能。(これを紹介したかった)
as = (3..23) % 4 => ((3..23).%(4)) as.class => Enumerator::ArithmeticSequence
公差が0の時はエラー
as = (3..23) % 0 => `%': step can't be 0 (ArgumentError)
特に%の方は短くかけて便利そうじゃないですか? AtCoderとかで使えそうだなと思いました。
まとめ
(3..23) % 4
がかっこいいから紹介したかっただけ。
https://docs.ruby-lang.org/ja/latest/class/Range.html#I_--25