Menu

backwards regEx and getTag

Help
Moon
2017-07-27
2017-07-27
  • Moon

    Moon - 2017-07-27

    Hi.

    I want to do a regEx search backwards to find the first match above the caret and extract the resulting regEx groups.

    I don't think I understand getTag properly... I can't even figure out how to get a count of the number of groups it contains!?

    I've tried several different methods - only some of them find a match backwards and none of them return the groups... can someone give me a firm shove in the right direction please?

    Here is what I've tried...

    import re
    
    def match_found(m):
        console.write("research: @ pos " + str(m.span(0)) + " groups: " + str(m.groups()) + "\n")
    
    console.write("research fwd\n")
    editor.research("^function (.*)\((.*)\)", match_found, FINDOPTION.REGEXP, 6000 , 6200)
    
    console.write("research bk\n")
    editor.research("^function (.*)\((.*)\)", match_found, FINDOPTION.REGEXP, 6200 , 6000)
    

    Search forward finds the match and gives me the groups, search backwards gives me nuthin...

    research fwd
    research: @ pos (6048, 6086) groups: ('CheckNeighbors', 'ent, itemname')
    research bk
    

    So I try with findText...

    (startPos, endPos) = editor.findText(FINDOPTION.REGEXP, 6000, 6200, "^function (.*)\((.*)\)")
    console.write("\nfindText fwd: @ pos " + str(startPos) + "\ngroup 1 = " + editor.getTag(1) + "\ngroup 2 = " + editor.getTag(2))
    
    (startPos, endPos) = editor.findText(FINDOPTION.REGEXP, 6200, 6000, "^function (.*)\((.*)\)")
    console.write("\nfindText bk: @ pos " + str(startPos) + "\ngroup 1 = " + editor.getTag(1) + "\ngroup 2 = " + editor.getTag(2))
    

    Search forward is good. Search backwards finds a match but getTag is not returning the groups:

    findText fwd: @ pos 6048
    group 1 = CheckNeighbors
    group 2 = ent, itemname
    findText bk: @ pos 6048
    group 1 = 
    group 2 = 
    

    and searchInTarget:

    editor.setTarget(6000, 6200)
    editor.setSearchFlags(FINDOPTION.REGEXP)
    rt = editor.searchInTarget("^function (.*)\((.*)\)")
    console.write("\nsearchInTarget fwd: @ pos " + str(rt) + "\ngroup 1 = " + editor.getTag(1) + "\ngroup 2 = " + editor.getTag(2))
    
    editor.setTarget(6200, 6000)
    editor.setSearchFlags(FINDOPTION.REGEXP)
    rt = editor.searchInTarget("^function (.*)\((.*)\)")
    console.write("\nsearchInTarget bk: @ pos " + str(rt) + "\ngroup 1 = " + editor.getTag(1) + "\ngroup 2 = " + editor.getTag(2))
    

    gives same result as findText =

    searchInTarget fwd: @ pos 6048
    group 1 = CheckNeighbors
    group 2 = ent, itemname
    searchInTarget bk: @ pos 6048
    group 1 = 
    group 2 = 
    

    last try was searchNext/searchPrev:

    editor.setCurrentPos(6000)
    editor.searchAnchor()
    rt = editor.searchNext(FINDOPTION.REGEXP, "^function (.*)\((.*)\)")
    console.write("\nsearchNext: @ pos " + str(rt) + "\ngroup 1 = " + editor.getTag(1) + "\ngroup 2 = " + editor.getTag(2))
    
    editor.setCurrentPos(6200)
    editor.searchAnchor()
    rt = editor.searchPrev(FINDOPTION.REGEXP, "^function (.*)\((.*)\)")
    console.write("\nsearchPrev: @ pos " + str(rt) + "\ngroup 1 = " + editor.getTag(1) + "\ngroup 2 = " + editor.getTag(2))
    

    No joy here either:

    searchNext: @ pos 6048
    group 1 = CheckNeighbors
    group 2 = ent, itemname
    searchPrev: @ pos 6048
    group 1 = 
    group 2 =
    

    Thanks.

     

    Last edit: Moon 2017-07-27
  • CFrank

    CFrank - 2017-07-27

    Not quite sure if I understand your question correctly.
    getTag doesn't provide a functionality to retrieve "submatches" (results when using regex like (hello).(world) where hello would be the first and world the second "submatch".
    If you still want to use getTag, than you have to loop over it and as soon as you receive
    an empty string your done.

    In order to retrieve this, I would, for example, use a match object and lastindex property.

    Concerning the backward search, why not using current position as the end attribute and
    let's say 0 or any less number than current position as the start attribute? When list of matches resturns than
    either use reverse call to iterate backwards or use last index from list ([-1]) to get the
    nearest match.

    Cheers
    Claudia

     

    Last edit: CFrank 2017-07-27
  • Sasumner

    Sasumner - 2017-07-27

    Backward regular expression searches are problematic. The Notepad++ user interface prohibits them directly (when you change "Search Mode" to "Regular Expression", the "up" direction is cleared and disabled). Perhaps that is why this code produces output:

    editor.research('a', match_found, 0, 0, editor.getTextLength())

    but this does not:

    editor.research('a', match_found, 0, editor.getTextLength(), 0)

    (assumes 'a' is in your document)

     

    Last edit: Sasumner 2017-07-27
  • Sasumner

    Sasumner - 2017-07-27

    I forgot my "match_found" function from the previous post:

    def match_found(m): print m.span(0)

     
  • Moon

    Moon - 2017-07-27

    Thanks both for looking at this.

    @Claudia
    The getTag function does appear to return the required submatches when searching forward, but not when searching backwards.

    My requirement is to extract the function-name as one regEx group and the function-parameters as a 2nd group from this example line (at pos 6048 of my test doc)...

    function CheckNeighbors(ent, itemname)

    Looking specifically at the findText test in my original post above (now highlighted in red), the exact same search is run forwards and backwards... it finds the regEx match in both cases but getTags only returns the required groups in the forward run.

    Given Sasumner's observation above, and my repeating of the issue in npp LuaScript, I've opted to npp/scintilla regex searchPrev to find the required line but then using python regex (searching forward!) to extract the required groups.

     

    Last edit: Moon 2017-07-27
  • CFrank

    CFrank - 2017-07-28

    @Moon, After rereading my post I guess I was a bit unclear - yes, getTag(number) rerturns a submatch but there is no function to retrieve how many submatches were catched.
    Sorry for confusion.

     

Log in to post a comment.