[Tutor] Regular Expression help - parsing AppleScript Lists as Strings

Kent Johnson kent37 at tds.net
Thu Nov 1 14:14:26 CET 2007


Kent Johnson wrote:
> You might want to look at doing this with pyparsing, I think it will 
> make it easier to get the data out vs just recognizing the correct pattern.

Here is a pyparsing version that correctly recognizes all of your 
patterns and returns a (possibly nested) Python list in case of a match.

Note that this version will parse lists that are nested arbitrarily 
deeply. If you don't want that you will have to define two kinds of 
lists, a singly-nested list and a non-nested list.

Kent

from pyparsing import *

List = Forward()
T = Literal('true').setParseAction( lambda s,l,t: [ True ] )
F = Literal('false').setParseAction( lambda s,l,t: [ False ] )
String = QuotedString('"')
Number = Word(nums).setParseAction( lambda s,l,t: [ int(t[0]) ] )
List << Literal('{').suppress() + 
delimitedList(T|F|String|Number|Group(List)) + Literal('}').suppress()

def IsASList(s):
    # AppleScript lists are bracked by curly braces with items separate 
by commas
    # Each item is an alphanumeric label(?) or a string enclosed by
    # double quotes or a list itself
    # e.g. {2, True, "hello"}
    try:
        parsed = List.parseString(s)
        return parsed.asList()
    except Exception, e:
        return None

sample_strs = [
    '{}',      # Empty list
    '{a}',     # Should not match
    '{a, b, c}', # Should not match
    '{"hello"}',
    '{"hello", "kitty"}',
    '{true}',
    '{false}',
    '{true, false}',
    '{9}',
    '{9,10, 11}',
    '{93214, true, false, "hello", "kitty"}',
    '{{1, 2, 3}}',  # This matches
    '{{1, 2, "cat"}, 1}',  # This matches

     # These don't match:
    '{{1,2,3},1,{4,5,6},2}',
    '{1, {2, 3, 4}, 3}',
    '{{1, 2, 3}, {4, 5, 6}, 1}',
    '{1, {1, 2, 3}}',  # Should match but doesn't
    '{93214, true, false, "hello", "kitty", {1, 2, 3}}',  # Should match 
but doesn't
    '{label: "hello", value: false, num: 2}',  # AppleScript dictionary 
- should not match
]

for sample in sample_strs:
    result = IsASList(sample)
    print 'Is AppleScript List:  %s;   String:  %s' % (bool(result), sample)
    if result:
        print result


More information about the Tutor mailing list