View Full Version : Interesting challenge...
jemfinch
10-09-2002, 02:08 AM
I don't really have time for this myself, I don't think, but you guys might find this (http://groups.google.com/groups?threadm=d1f767c3.0210040915.3e695631%40posting.google.com) challenge interesting.
Jeremy
That's pretty neat. I noticed the thread on usenet, but didn't check it. Maybe if I have some more time later I can check it out. All in all, it doesn't look very hard to write a program to solve it.
Halide
10-09-2002, 11:10 AM
cool
i have some newbie questions though from this code:
from __future__ import generators
def solve_equation(equation, x, replace="X", replacewith="123456890"):
"""Solve the equation for any permutation of the replacement characters
for the replace character in x."""
supplied_digits = {}
for i in range(len(x)):
if x[i] != replace:
supplied_digits[i] = x[i]
assert len(x) - len(supplied_digits) == len(replacewith)
for i in permIter(replacewith):
p = i
keys = supplied_digits.keys()
keys.sort()
for pos in keys:
p = p[:pos] + supplied_digits[pos] + p[pos:]
if eval(equation):
yield p
def permIter(seq):
"""Given some sequence 'seq', returns an iterator that gives
all permutations of that sequence.
Source: http://aspn.activestate.com/ASPN/Cookbook/Python/Recipe/105962
"""
## Base case
if len(seq) == 1:
yield(seq[0])
raise StopIteration
## Inductive case
for i in range(len(seq)):
element_slice = seq[i:i+1]
rest_iter = permIter(seq[:i] + seq[i+1:])
for rest in rest_iter:
yield(element_slice + rest)
raise StopIteration
# --------------------------------------------------------------------------
---
# Using it
# --------------------------------------------------------------------------
---
a = "7XX"
b = "XX"
c = "XXXXX"
replace = "X"
replacewith = "123456890"
equation = "int(p[0:3]) * int(p[3:5]) == int(p[5:10])"
equation_print = "'%s * %s == %s' % (p[0:3], p[3:5], p[5:10])"
for p in solve_equation(equation, a+b+c, replace, replacewith):
print eval(equation_print)
a = "XXX"
b = "XX"
c = "XXXXX"
replace = "X"
replacewith = "1234567890"
equation = "int(p[0:3]) * int(p[3:5]) == int(p[5:10])"
equation_print = "'%s * %s == %s' % (p[0:3], p[3:5], p[5:10])"
for p in solve_equation(equation, a+b+c, replace, replacewith):
print eval(equation_print)
* what is 'assert'
* dict.keys() returns a list of keys in dict?
* what is 'yield'
* what does 'raise StopIteration' do
this code is interesting (for me atleast) :)
what is 'assert' -> assert(x) says, "If x isn't true, I'm screwed! So if it's not true, raise an error."
dict.keys() returns a list of keys in dict? Yeah
what is 'yield' Okay, this is a little complicated, and I'm probably going to answer it wrong and then jeremy will yell at me but here goes. (First, I'll mention that it's what generators do, so if you want the full answer, read about generators at python.org).. look at it this way .. A function that does a yield returns an iteration over a list, so yeild is like "return", except the function doesn't actually return. it returns the yeilded value and goes on executing until it reaches the end of the function.. so the function will generally yield multiple values before returning.
Okay, in retrospect, that was a shitty way of explaining it... go to the python.org Description for yield (http://www.python.org/dev/doc/devel/ref/yield.html) for a much better answer.
what does 'raise StopIteration' do Okay, this has to do with exception handling. If you're unfamiliar with exception handling, I'm going to again direct you to python.org since I'd just be "reinventing the explanation" (if you will) ... Read this page (http://www.python.org/dev/doc/devel/ref/try.html), then understand that when they talk about something raising an exception, that's what that line of code is doing.
Enjoy! :)
jemfinch
10-09-2002, 12:12 PM
I can't read add much to Python.org's description of iterators, so I won't.
One important thing to note about "raise StopIteration" is that it's the way one stops an iteration :)
Jeremy
vBulletin® v3.7.0, Copyright ©2000-2009, Jelsoft Enterprises Ltd.