In [3]:
import forge
from data import warehouse
from puzzle.puzzlepedia import prod_config
prod_config.init()

trie = warehouse.get('/words/unigram/trie')

In [4]:
word = 'CHEAPSKATE'
targets = []
for x in reversed(range(2, round(len(word) / 2) + 1)):
  targets.append((x, len(word) - x))
print(targets)


[(5, 5), (4, 6), (3, 7), (2, 8)]

In [15]:
from data.seek_sets import chain_seek_set

def process(word, interesting=set(), required=None, length=None):
  word = word.lower()
  seek_set = chain_seek_set.ChainSeekSet(list(word), len(word))
  if length:
    lengths = [(length, len(word) - length)]
  else:
    lengths = targets(word)
  for target in lengths:
    if required and len(required) not in target:
      continue
    for result in walk(seek_set, [], target):
      parts = result.split()
      if required and required not in parts:
        continue
      a, b = parts
      if a in interesting or b in interesting:
        flag = '*'
      else:
        flag = ' '
      print('%s %s (%s)' % (flag, result, word))

def targets(word):
  targets = []
  for x in reversed(range(2, round(len(word) / 2) + 1)):
    targets.append((x, len(word) - x))
  return targets

def walk(seek_set, acc, targets, pos=0):
  if pos >= len(targets):
    yield ' '.join(acc)
    return
  target = targets[pos]
  seek_set.set_length(target)
  for result, weight in trie.walk(seek_set, exact_match=True):
    if weight < 5e4:
      break
    acc.append(result)
    yield from walk(seek_set[result:], acc, targets, pos+1)
    acc.pop()

In [7]:
process('ANTINRTLANOID', )


  indian tarlton (antinrtlanoid)
  inland tration (antinrtlanoid)
  intron lindata (antinrtlanoid)
  linton radiant (antinrtlanoid)
  tintin arnaldo (antinrtlanoid)
  andnot ritalin (antinrtlanoid)
  tannin dilator (antinrtlanoid)
  tandon ritalin (antinrtlanoid)
  titian norland (antinrtlanoid)
  dannii tarlton (antinrtlanoid)
  darton lintian (antinrtlanoid)
  tinton irlanda (antinrtlanoid)
  tinton darlina (antinrtlanoid)
  indain tarlton (antinrtlanoid)
  danton ritalin (antinrtlanoid)
  nordin atitlan (antinrtlanoid)
  dannil tration (antinrtlanoid)
  lannan diritto (antinrtlanoid)
  niland tration (antinrtlanoid)
  raton dilantin (antinrtlanoid)
  trond nainital (antinrtlanoid)
  torna dilantin (antinrtlanoid)

In [5]:
process('FREQUENCIES')


  squire fence (frequencies)
  risque fence (frequencies)
  cinque reefs (frequencies)
  cinque frees (frequencies)
  squier fence (frequencies)
  quince reefs (frequencies)
  quince frees (frequencies)
  quence fires (frequencies)
  quence fries (frequencies)
  quence serif (frequencies)
  quence frise (frequencies)
  quires fence (frequencies)
  fence squire (frequencies)
  fence risque (frequencies)
  fence squier (frequencies)
  fence quires (frequencies)
  fires quence (frequencies)
  fries quence (frequencies)
  serif quence (frequencies)
  reefs cinque (frequencies)
  reefs quince (frequencies)
  frees cinque (frequencies)
  frees quince (frequencies)
  frise quence (frequencies)
  fire quences (frequencies)
  if sequencer (frequencies)

In [1]:
process('ANTINRELANOID')


---------------------------------------------------------------------------
NameError                                 Traceback (most recent call last)
<ipython-input-1-78f382c4e52c> in <module>()
----> 1 process('ANTINRELANOID')

NameError: name 'process' is not defined

In [30]:
process('LYINGDOWN')


(4, 5)
long windy
down lying
(3, 6)
(2, 7)
in goldwyn

In [31]:
process('NONJURY')


(4, 3)
(3, 4)
(2, 5)

In [32]:
process('POWERPACK')


(4, 5)
pack power
(3, 6)
pop wacker
cow keppra
(2, 7)
we propack

In [33]:
process('APPEALING')


(4, 5)
page plain
page palin
plan paige
pain plage
gain apple
gain appel
gain papel
pile pagan
(3, 6)
age lappin
leg appian
leg papain
gap alpine
gap nepali
gap plaine
gap pineal
gap pelian
gap lapine
pen paglia
lip pangea
pig alpena
lap pagine
(2, 7)

In [34]:
process('ENAMORING')


(4, 5)
more nagin
name groin
name ringo
game ronin
main negro
main norge
main regno
near mingo
mean groin
mean ringo
ring eamon
iron megan
iron gmane
iron amgen
iron mange
mine organ
mine argon
mine goran
mine groan
mine orang
mine rogan
nine margo
rain gnome
earn mingo
norm angie
grin eamon
(3, 6)
one margin
one garmin
one ingram
one arming
one ingmar
man region
man ignore
man origen
man orgien
age mornin
ago renmin
ago minner
nor enigma
nor imagen
nor ingame
aim negron
arm onegin
era mignon
ear mignon
(2, 7)
in marengo
in morgane
in germano
in garnome
on germain
on reaming
on ingemar
or meaning
no germain
no reaming
no ingemar
re moaning
re maginon
go riemann
go reimann
go amerinn
mr gennaio

In [35]:
process('AGREEABLE')


(4, 5)
area glebe
able agree
able eager
able agere
gear beale
gear albee
bear eagle
beer algae
bare eagle
rage beale
rage albee
(3, 6)
era beagle
ear beagle
bee galera
beg aleera
(2, 7)
be realage

In [1]:
process('compared')


---------------------------------------------------------------------------
NameError                                 Traceback (most recent call last)
<ipython-input-1-cfc89d6c2449> in <module>()
----> 1 process('compared')

NameError: name 'process' is not defined

In [66]:
from nltk.corpus import wordnet
from data import warehouse
word_api = warehouse.get('/api/words')

In [93]:
extras = {'shy', 'red', 'gel', 'lest', 'ed'}
interesting = extras.union(fruits)

In [90]:
def syns(word, target_len):
  word = word.lower()
  process(word, interesting)
  for w in word_api.synonyms(word):
    if len(w) == target_len:
      process(w, interesting)

In [92]:
syns('DISTENDED', 7)


  need didst (distended)
* seed didnt (distended)
  tend sided (distended)
  wide end (widened)
  end wide (widened)
  we dined (widened)
  able dot (bloated)
  load bet (bloated)
  beat old (bloated)
  bold eat (bloated)
  bold tea (bloated)
  old beat (bloated)
  eat bold (bloated)
  tea bold (bloated)
  dot able (bloated)
  bet load (bloated)
  to blade (bloated)
  to abdel (bloated)
  at doble (bloated)
  do table (bloated)
  we dells (swelled)
  seem cut (tumesce)
  stem cue (tumesce)
  cut seem (tumesce)
  cue stem (tumesce)

In [64]:
def clean(s):
  # Convert "dried_fruit.n.01" to "driedfruit".
  return s.name().split('.')[0].replace('_', '')

def collect(acc, lemma):
  s = wordnet.synset(lemma)
  for f in s.hyponyms():
    acc.add(clean(f))
  
fruits = set()
collect(fruits, 'edible_fruit.n.01')
collect(fruits, 'fruit.n.01')
fruits.remove('ear')
for fruit in sorted(fruits):
  print(fruit)


accessoryfruit
achene
ackee
acorn
aggregatefruit
anchovypear
apple
apricot
avocado
banana
barbadosgooseberry
berry
breadfruit
buckthornberry
buffalonut
canistel
carambola
carissaplum
ceriman
cherry
chokecherry
citrus
cling
cocoaplum
cubeb
custardapple
date
driedfruit
drupe
durian
ediblefruit
elderberry
feijoa
fig
freestone
fruitlet
garambulla
genip
genipap
gourd
grape
guava
hagberry
hip
hogplum
jaboticaba
jackfruit
jujube
juniperberry
kaiapple
ketembilla
kiwi
lanseh
litchi
longanberry
loquat
mamey
mango
mangosteen
marang
marasca
mayapple
medlar
melon
mombin
nectarine
olive
papaw
papaya
passionfruit
peach
pear
pineapple
pitahaya
plum
plumcot
pod
pome
pomegranate
prairiegourd
pricklypear
pulasan
pyxidium
quandong
quince
rambutan
roseapple
rowanberry
sapodilla
sapote
schizocarp
seed
sorb
sourgourd
tamarind
tangelo
wildcherry
windfall

In [58]:
from data import warehouse
anagram_index = warehouse.get('/words/unigram/anagram_index')

def scramble(bases, extra):
  for base in bases:
    search = base + extra
    if search not in anagram_index:
      continue
    for result in anagram_index[base + extra]:
      print(result, '=', base, '+', extra)

In [60]:
scramble(fruits, 'gel')


longacre = acorn + gel
solberg = sorb + gel

In [95]:
candidates = """
shy gel lest
""".split()
for w in candidates:
  print(w)
  scramble(fruits, w.lower())


shy
gel
longacre = acorn + gel
solberg = sorb + gel
lest
loveliest = olive + lest
lobsters = sorb + lest
bolsters = sorb + lest
leapster = pear + lest
prelates = pear + lest

In [100]:
candidates = """
entailing faltering filtering flagstone flowering forgetful galleries gargoyles gauntlets genealogy generally geniality genitalia gentleman gentlemen genuinely geologist ghastlier glaciated glassware gleanings gleefully glistened glorified glorifies glowering glutamate godliness graticule greyscale grovelled guardedly guerrilla guessable guideline guillemot heralding hexagonal ignorable illegally illegible impelling indulgent inelegant integrals irregular jestingly knowledge labelling lamenting languages largeness laughable leavening lecturing leeringly legalised legendary legionary legislate legstraps lengthier lessening lethargic lettering levelling licensing ligatured ligatures lightened lightness limelight lingering listening littering loitering longevity longitude loosening lumbering mellowing modelling molesting monologue neglected negligent neologism overlying panelling parleying pedalling pigtailed ploughers ploughmen privilege prologise prologize prologues prolonged ravelling realising realizing rebelling recalling reclining recoiling rectangle recycling refilling refluxing regretful regularly regulated regulates regulator releasing relegated relegates relieving religions religious relinking reloading repelling replacing replaying replugged resolving resulting retelling revealing revolting revolving rigmarole sacrilege salesgirl seedlings seemingly selecting shielding sidelight sightless signalled silencing singleton slaughter slavering slightest soldering spellings spillages squealing strangely strangled strangler strangles struggled struggles sugillate swellings tailgates telegrams telegraph trembling triangles trilogies unaligned underling unfeeling unplugged unsealing unveiling upwelling vegetable vestigial vigilance villagers welcoming wellbeing weltering wrestling yellowing
""".split()
for c in candidates:
  process(c, interesting, required='gel')

In [102]:
import forge
from puzzle.puzzlepedia import puzzlepedia

puzzle = puzzlepedia.parse("""
mppgao
rn
ldp
abcdefghijklmnopqrstuvwxyz
i
mppgao
eem
arerpl
mppgao
nuaapi
eem
gncplv
abcdefghijklmnopqrstuvwxyz
rg
""", hint='acrostic')

In [18]:
process('herpameis')


  same hiper (herpameis)
  rape imesh (herpameis)
  hear mepis (herpameis)
  seem phair (herpameis)
  peer amish (herpameis)
  peer misha (herpameis)
  mere aphis (herpameis)
  his ampere (herpameis)
  she premia (herpameis)
  she mperia (herpameis)
  map heiser (herpameis)
  him pearse (herpameis)
  him speare (herpameis)
  him espera (herpameis)
  him sapere (herpameis)
  aim sphere (herpameis)
  aim herpes (herpameis)
  hip sameer (herpameis)
  hip meares (herpameis)
  hip mersea (herpameis)
  pie ramesh (herpameis)
  pie shmera (herpameis)
  pie masher (herpameis)
  pie rhames (herpameis)
  ash empire (herpameis)
  he impresa (herpameis)
  me sharpie (herpameis)
  me saphire (herpameis)
  hi empresa (herpameis)
  hi amperes (herpameis)
  ie hampers (herpameis)
  ha premise (herpameis)
  ha empires (herpameis)
  ha siempre (herpameis)
  ha imprese (herpameis)
  ah premise (herpameis)
  ah empires (herpameis)
  ah siempre (herpameis)
  ah imprese (herpameis)

In [124]:
print('\t'.join('O S I U B L E R A M I S H T E'.split()))


O	S	I	U	B	L	E	R	A	M	I	S	H	T	E

In [ ]: