素歩人徒然 眼科の待合室で考えた Perlプログラム クイズ
素歩人徒然
(156)

眼科の待合室で考えた


── クイズを解くならPerlで

 年に一度の眼科検診を受けてきた。結論から言うと異常なし。医師が言うには「どこにも異常はないから人間ドックでの検診を受けていれば特別な検診は必要ないでしょう」とのことであった。人間ドックで引っかかって、緑内障の可能性とか白内障の気味があるとか脅かされつつ、ここ10年程毎年精密検査を受け続けてきたのであるが、やっと無罪放免となった訳である。

 私は、検診のとき瞳孔を開くための目薬をさされると細かい字が読めなくなる。更にその後遺症で毎年苦労しているのでそれから解放されるのは大変ありがたいことだと思う。私はこの目薬をさされると4〜5日は眼が充血し細かいものを見ることができなくなる(それも左目だけ!)。眼がチカチカして細かい字など読めなくなるから、今日は待ち時間に読むための書物や新聞などを持参しなかった。待たされている間に何もすることがない。どうするか。そうだ、あの問題を考えることにしよう。

 その問題というのは、友人八卷氏がFacebook上に提起した次のような問題である。

?*(?-?/?)=10 の?には一桁の異なる整数が入る

 つまり ? に入る整数を求めよという問題である。私はこの問題に取り組んで待ち時間を有効に過ごすことにした。こういう問題を考えるのが私は大好きであるが、解けたと思って喜び勇んで答えを投稿すると、あに図らんや大抵は間違っていて恥をかくことになる。それでも楽しいと思う。

 そういった失敗は問題を良く読んでいないから起るのだと思う。たとえば、ここでは「整数」とは何かをよく考える必要がある。当然負数も含まれることになるから気を付けよう。“/”で表現された「割り算」が含まれているが、普通コンピュータに詳しければ、どのような割り算なのか(つまり整数割り算か実数の割り算か)を考えることになる。それからゼロによる割り算が発生しないよう注意することも必要であろう。

 しかしこの問題ではそういう細部には一切触れられていない。ということは、特別な制限の付かない一般的な割り算だと解釈しなければならない。問題はより一層難しくなる。そういう時はPerl言語を使うのが一番良い。これはPerlで解くのに適した問題だ。それなら自分にも解けそうな気がする。

 帰宅後、すぐさまコンピュータに向かってプログラム作りを始めることになった(眼がよく見えないというのに)。その結果できあがったプログラムが以下のものである。

#!/usr/local/bin/perl
# (c) 2017-11-14 : Coded by shun kinoshita / knuhs
#
# 問題(八卷直一さんがFacebook上で提示したもの)
# ?*(?-?/?)=10 の?には一桁の異なる整数が入ります。
#
use strict;
my $count=0;

     for( my $a=-9; $a<=9; $a++ )
     {
          for( my $b=-9; $b<=9; $b++ )
          {
               next if $a==$b ;
               for( my $c=-9; $c<=9; $c++ )
               {
                    next if $a==$c | $b==$c ;
                    for( my $d=-9; $d<=9; $d++ )
                    {
                         next if $a==$d | $b==$d | $c==$d | $d==0 ;
                         next if $a*($b-$c/$d)!=10 ;
                         $count++;
                         print "[$count]:($a)*(($b)-($c)/($d))";
                         my $v = $a * ( $b - $c / $d );
                         print " = $v\n";
                    }
               }
          }
     }
     print "Total counts = $count\n";
     exit;
     
(図:Perlプログラム)

 実行して見ると439個の解が得られた!! しかも、一度の実行ですぐ解が得られのだから、ものすごく気分が良い。これぞプログラム作りの醍醐味と言えるであろう。やはり考察に十分時間をかけたからだと思いたい。

 ただ、このプログラムは私の期待通りに動作したと言えるが、それがこの問題の正解は何なのかどうか、それは私にも分からない。



【追記】
このPerlプログラムの最新版(コメントを付加)は intValue.pl で参照できます。

プログラムの<実行結果>はこうなりました。

このプログラムもPerl Program集(私の作ったPerlプログラム)として収録されています。