summaryrefslogtreecommitdiff
path: root/src/examples/rangeCheck.py
diff options
context:
space:
mode:
authorPaul McGuire <ptmcg@austin.rr.com>2015-12-31 00:55:47 +0000
committerPaul McGuire <ptmcg@austin.rr.com>2015-12-31 00:55:47 +0000
commit401ba4a945b88f12e26495a82d4059d4adbaec92 (patch)
tree9570287813d7358750ddd1ffe50ba60c0a999972 /src/examples/rangeCheck.py
parentc8e8c6592d625d24bc7c0ca34bcc527ec380c2d5 (diff)
downloadpyparsing-git-401ba4a945b88f12e26495a82d4059d4adbaec92.tar.gz
Added new example parseTabularData.py
Updated several examples to more current Python and pyparsing practices (and better Py2/Py3 cross-compatibility)
Diffstat (limited to 'src/examples/rangeCheck.py')
-rw-r--r--src/examples/rangeCheck.py43
1 files changed, 20 insertions, 23 deletions
diff --git a/src/examples/rangeCheck.py b/src/examples/rangeCheck.py
index 35c9ef3..59bd49c 100644
--- a/src/examples/rangeCheck.py
+++ b/src/examples/rangeCheck.py
@@ -3,46 +3,42 @@
# A sample program showing how parse actions can convert parsed
# strings into a data type or object, and to validate the parsed value.
#
-# Copyright 2011, Paul T. McGuire
+# Updated to use new addCondition method and expr() copy.
+#
+# Copyright 2011,2015 Paul T. McGuire
#
from pyparsing import Word, nums, Suppress, ParseException, empty, Optional
from datetime import datetime
-def rangeCheck(minval=None, maxval=None):
+def ranged_value(expr, minval=None, maxval=None):
# have to specify at least one range boundary
if minval is None and maxval is None:
raise ValueError("minval or maxval must be specified")
-
+
# set range testing function and error message depending on
# whether either or both min and max values are given
- inRangeFn = {
- (True, False) : lambda x : x <= maxval,
- (False, True) : lambda x : minval <= x,
- (False, False) : lambda x : minval <= x <= maxval,
+ inRangeCondition = {
+ (True, False) : lambda s,l,t : t[0] <= maxval,
+ (False, True) : lambda s,l,t : minval <= t[0],
+ (False, False) : lambda s,l,t : minval <= t[0] <= maxval,
}[minval is None, maxval is None]
outOfRangeMessage = {
- (True, False) : "value %%s is greater than %s" % maxval,
- (False, True) : "value %%s is less than %s" % minval,
- (False, False) : "value %%s is not in the range (%s to %s)" % (minval,maxval),
+ (True, False) : "value is greater than %s" % maxval,
+ (False, True) : "value is less than %s" % minval,
+ (False, False) : "value is not in the range (%s to %s)" % (minval,maxval),
}[minval is None, maxval is None]
- # define the actual range checking parse action
- def rangeCheckParseAction(string, loc, tokens):
- parsedval = tokens[0]
- if not inRangeFn(parsedval):
- raise ParseException(string, loc, outOfRangeMessage % parsedval)
-
- return rangeCheckParseAction
+ return expr().addCondition(inRangeCondition, message=outOfRangeMessage)
# define the expressions for a date of the form YYYY/MM/DD or YYYY/MM (assumes YYYY/MM/01)
integer = Word(nums).setName("integer")
integer.setParseAction(lambda t:int(t[0]))
-month = integer.copy().addParseAction(rangeCheck(1,12))
-day = integer.copy().addParseAction(rangeCheck(1,31))
-year = integer.copy().addParseAction(rangeCheck(2000, None))
-
+month = ranged_value(integer, 1, 12)
+day = ranged_value(integer, 1, 31)
+year = ranged_value(integer, 2000, None)
+
SLASH = Suppress('/')
dateExpr = year("year") + SLASH + month("month") + Optional(SLASH + day("day"))
dateExpr.setName("date")
@@ -53,7 +49,7 @@ dateExpr.setParseAction(lambda t: datetime(t.year, t.month, t.day or 1).date())
# add range checking on dates
mindate = datetime(2002,1,1).date()
maxdate = datetime.now().date()
-dateExpr.addParseAction(rangeCheck(mindate, maxdate))
+dateExpr = ranged_value(dateExpr, mindate, maxdate)
tests = """
@@ -62,6 +58,7 @@ tests = """
2004/2/29
2004/2/30
2004/2
+ 1999/12/31
""".splitlines()
for t in tests:
t = t.strip()
@@ -71,6 +68,6 @@ for t in tests:
print(dateExpr.parseString(t)[0])
except Exception as e:
print(str(e))
- print()
+ print('')