pythonregexdictionarylogic-programmingunify

Creating relations with unify and regular expression


I'm trying to create a relation with unify for example:

Boy(Mike) --> Mike is a boy

Girl(Lisa) --> Lisa is a girl

isSister(Mike,Lisa) --> Lisa is Mike's sister

and this is my code:

from fact import Fact
from logic import get, unify, var

from itertools import chain 
import regex as re


facts = {}

pattern = r"(\w+)\((?:([^,\)]+)\,(?:([^,\)]+)))+\)\.?"

rule = input('Ingrese un hecho o consulta:')
while rule != '!':
  match = re.match(pattern, rule)
  print(match)
  name = match.captures(1)[0]
  argument1 = match.captures(2)
  argument2 = match.captures(3)
  if rule.endswith('.'):
    if not name in facts:
      facts[name] = Fact()
    facts[name].append(argument1[0])
    facts[name].append(argument2[0])
  else:
    X = var()
    Y = var()
    for _ in facts[name](X,Y): print(get(X),get(Y))
  rule = input('Ingrese un hecho o consulta:')

What I want, is that when I ask for isSister(?,Lisa), it returns Mike. This is what I get:

Traceback (most recent call last): File "main.py", line 17, in name = match.captures(1)[0] AttributeError: 'NoneType' object has no attribute 'captures'


Solution

  • match returns None if there is no match, and this appears to happen somewhere in your while loop. You'll need to handle this case somehow, either by:

    if match == None:
        # handle
    

    or:

    try:
       name=match.captures(1)[0]
    except AttributeError as e:
        # handle
    

    It's up to you to pick the handling that fits your solution, but these are the two patterns I generally go for. There are others I'm sure, but I would suggest starting here.