I am wondering how to parse the structures that are in the middle of a sentence.
Consider this example.
"Please join me on Fifteenth of May 2017 at three PM for a cup of coffee."
Here, I have the lark grammar to parse date -> "Fifteenth of May 2017 at three PM"
Where the structure needs to parse is inside a sentence.
Is it possible to create a rule that can search for a pattern and parse it ?
There is no such mechanism in Lark, right now.
Your best bet is to try to parse from each position (catching the exceptions), until the parse succeeds.
If should mention that pyparsing does have such a feature. I believe they call it scan.
Any examples? Because "Please" "join" "me" "on" are not included in the parse tree it will produce ab exception saying Please is not included in the symbols similar. Again this would be kind of string matching then ?
Another approach is
start: /.*/ rule rule rule /.*/
Only works with parser="earley", lexer="dynamic_complete"
from lark import Lark
grammar = """
status : /.*/ starter /.*/
starter: STARTER? [date]
STARTER: /(?:[a-zA-Z'-]+[^a-zA-Z'-]+){1,20}/
date: [relative][number] [bet][dayes] [part] [month] [year] [hour]
number: NUMBER [dayes]
part: PART
month: [bet] MONTH [number] [bet] [MONTH]
relative: RELATIVE
year: YEAR
hour: [number] [relative] HOUR
HOUR:"hours"|"hrs"|"hour"
dayes: [PART][NUMBER][RELATIVE]DAYES [bet] [DAYES] [NUMBER] [PART][MONTH] [NUMBER] [partday]
partday: [relative]PARTDAY
bet:BET
BET: "between"|"to"
DAYES:"day"|"monday"|"tuesday"|"wednesday"|"saturday"|"sunday"|"friday"|"thursday"|"today"|"tommorrow"
NUMBER:"first"|"second"|"third"|"fourth"|"fifth"|"seventh"|" twentith"
|"eighth"|"one"|"two"|"three"|"four"|"five"
PART: "of"|"in"|"at"
MONTH: "January"|"February"|"March"|"April"|"May"|"June"|"July"|"August"|"Spetember"|"October"|"November"|"December"
RELATIVE: "before"|"after" |"every"|"from"|"begining"|"end"|"by"
YEAR: "two thousand eight"|"two thousand nine"|"two thousand seventeen"|"two thousand eighteen"|"two thousand ninteen"
PARTDAY: "morning"|"evening"|"afternoon"|"midnight"
%import common.WS
%import common.ESCAPED_STRING
%ignore WS
"""
parser = Lark(grammar, parser='earley', start ='status', lexer= 'dynamic_complete' ) in parse tree!
st = " Hello monday afternoon parse me"
tree = parser.parse(st)
print(tree)
File "parsingdemo.py", line 61, in <module>
parser = Lark(grammar, parser='earley', start ='status', lexer= 'dynamic_complete' ) # Explicit ambiguity in parse tree!
File "/home/../anaconda3/lib/python3.6/site-packages/lark/lark.py", line 165, in __init__
self.parser = self._build_parser()
File "/home/../anaconda3/lib/python3.6/site-packages/lark/lark.py", line 188, in _build_parser
return self.parser_class(self.lexer_conf, parser_conf, options=self.options)
File "/home/../anaconda3/lib/python3.6/site-packages/lark/parser_frontends.py", line 122, in __init__
super(self).__init__(*args, complete_lex=True, **kw)
This leads to an error.
Please use branch 0.7b
Installed
Processing dependencies for lark-parser==0.6.5
Finished processing dependencies for lark-parser==0.6.5
return self.parser_class(self.lexer_conf, parser_conf, options=self.options)
File "/home/../anaconda3/lib/python3.6/site-packages/lark/parser_frontends.py", line 122, in __init__
super(self).__init__(args, complete_lex=True, *kw)
TypeError: super() argument 1 must be type, not XEarley_CompleteLex
same error persists!!
Use git to check out branch 0.7b
You can't install it with pip yet, because it hasn't been released
I cloned the repo and switch to the branch and did a pull then
git checkout 0.7b
Already on '0.7b'
Your branch is up-to-date with 'origin/0.7b'.
I ran `python3 setup.py install
Processing lark_parser-0.6.5-py3.6.egg
removing '/home/../anaconda3/lib/python3.6/site-packages/lark_parser-0.6.5-py3.6.egg' (and everything under it)
creating /home/../anaconda3/lib/python3.6/site-packages/lark_parser-0.6.5-py3.6.egg
Extracting lark_parser-0.6.5-py3.6.egg to /home/akr/anaconda3/lib/python3.6/site-packages
lark-parser 0.6.5 is already the active version in easy-install.pth
Installed /home/../anaconda3/lib/python3.6/site-packages/lark_parser-0.6.5-py3.6.egg
Processing dependencies for lark-parser==0.6.5
Finished processing dependencies for lark-parser==0.6.5
Remove and install it, just to make sure.
And check if the following code works for you (I just checked, and it works with current 0.7b, commit 76e185a):
from lark import Lark
p = Lark("""!start: "a"? "b"? "c"? """, lexer='dynamic_complete')
print(p.parse("bc"))
Yes.
Tree(start, [Token(B, 'b'), Token(C, 'c')]).
It does work.
So your code should work as well. Or at least give a different exception.
File "/home/../timeparsing/lark/lark/parser_frontends.py", line 90, in __init__
self._prepare_match(lexer_conf)
File "/home/../timeparsing/lark/lark/parser_frontends.py", line 112, in _prepare_match
raise ValueError("Dynamic Earley doesn't allow zero-width regexps", t)
ValueError: ("Dynamic Earley doesn't allow zero-width regexps", TerminalDef('__ANON_0', '.*'))
That support is also required, it seems like.
My bad, it shoudl be /.+/?
Tree(start, [Token(__ANON_0, ' Hello monday after'), Token(__ANON_0, 'noon parse me')])
It parsed the sentence without exception. However, the result is wrong.
Any way, now it supports above kind of sentence so we could close the issue.