私自身が表題の問題を解いた時のプログラムについて解説します。
問題の詳細は「同じ数を表示し続ける7セグメントディスプレイ」(CodeIQ)を参照してください。
7セグメントディスプレイは7箇所の点灯の有無で数字を表示します。
この7セグメントディスプレイを横に並べて数を表示したとき、点灯している場所を数え、各桁での個数の「積」を次に表示します。
例えば、「718」からスタートすると、「7」は3箇所、「1」は2箇所、「8」は7箇所が点灯しているので、3×2×7=42を計算し、次に「42」を表示します。
また、「42」において、「4」は4箇所、「2」は5箇所が点灯しているので、4×5=20より次に「20」を表示します。
次に「20」において、「2」は5箇所、「0」は6箇所が点灯しているので、5×6=30より次に「30」を表示します。
さらに「30」において、「3」は5箇所、「0」は6箇所が点灯しているので、5×6=30より次に「30」を表示します。
つまり、「718」から始まると「718」→「42」→「20」→「30」→「30」→…というように「30」が続くようになります。
このとき、登場する数は「718」「42」「20」「30」の4種類だけです。
標準入力から整数 n が与えられたとき、上記の処理を行って過去に表示した数が再度表示されるまで探索したとき、登場する数がいくつあるか求め、その数を標準出力に出力してください。
なお、n は符号なし32ビット整数型の範囲(0~4,294,967,295)とします。
【入出力サンプル】
標準入力
718
標準出力
4
Rubyで解答しています。
#!/usr/bin/ruby PTN = [6, 2, 5, 5, 4, 5, 6, 3, 7, 6] def count(n) ret = 1 loop{ m = n % 10 n /= 10 ret *= PTN[m] break if n == 0 } return ret end def solve(n) lst = {n => true} cnt = 0 loop{ cnt += 1 n = count(n) if lst[n] then break else lst[n] = true end } return cnt end # main while line = gets line.strip! next if line.empty? p solve(line.to_i) end
入力値を数値にしてsolve()に渡し、結果を印字します。
lstは{過去に現れた数 => true}という連想配列で、同じ数が現れたかのチェックに使います。
cntは繰り返しになるまでの回数で答えです。
lstに同じ数が現れるまでcount()を呼び出します。
同じ数が現れた時のcntを返します。
PTNには0〜9の各数の7セグメントディスプレイの点灯位置の数のリストです。
1桁ずつ数を求め、PTNから7セグメントディスプレイの点灯位置の数を求めて掛け合わせます。
最初にも書きましたがこの出題者の問題としてはものすごく簡単です。
何か引っ掛けがあるのかと疑うレベルでしたが、そんなものもありませんでした。