“SEND + MORE = MONEY”ソルバーを Squeak Smalltalk で その4

久しぶりに SEND + MORE = MONEY 。以前書いたもの(ブルートフォース版)の焼き直しなのですが、少しだけ趣を変えてみました。デュードニーの覆面算というのですね。

| int solveAlphametics |

int := [:array | array reversed polynomialEval: 10].

solveAlphametics := [:spec |
   | check ans |
   check := spec value: (ans := OrderedCollection new).
   (0 to: 9) combinations: check numArgs atATimeDo: [:digits |
      digits permutationsDo: [:param | check valueWithArguments: param]].
   ans asArray].

solveAlphametics value: [:ans | [:S :E :N :D :M :O :R :Y |
   | a b c |
   (({S. M} noneSatisfy: #isZero) and: [
      (a := int value: {S.E.N.D})
      + (b := int value: {M.O.R.E})
      = (c := int value: {M.O.N.E.Y})]) ifTrue: [ans add: {a. b. c}]]].
"=> #(#(9567 1085 10652)) "

solveAlphametics value: [:ans | [:W :D :O :T :G :L :E :C :M |
   | a b c |
   (({W. G. D} noneSatisfy: #isZero) and: [
      (a := int value: {W.W.W.D.O.T})
      - (b := int value: {G.O.O.G.L.E})
      = (c := int value: {D.O.T.C.O.M})]) ifTrue: [ans add: {a. b. c}]]].
"=> #(#(777589 188106 589483) #(777589 188103 589486)) "