def checkConstraints(src, tgt, sub_src, sub_tgt):
    ''' Checks if the rules satisfy the filtering constraints (without these the grammar would explode) '''

    # Return a default 'None' rule if any of the constraints is not satisifed

    # Substitute the nonterminal in both sides before checking the constraints
    # If the constraints are satisfied, then the modified rules are combined and returned
    X1_indx = src.find('X__1')
    if X1_indx != -1:
        # Check constraint-3: Rules are limited to five non-terminals and terminals on source side
        # Find the difference in length between the source phrase and sub-phrase,
        # if the length difference is more than TOT_TERMS (default 7), don't add it to the rulesTempSet
        if ( len(src.split()) - len(sub_src.split()) + 1 ) > tot_src_terms:
            return None

        # Constraint-4: The source side does **NOT** have two adjacent nonterminals
        #   The sub phrase should not be next to the existing non-terminal (X__1)
        adj_X1_right = sub_src + ' X__1'
        adj_X1_left = 'X__1 ' + sub_src
        if src.startswith(adj_X1_right) or src.find(' '+adj_X1_right) != -1 or \
           src.endswith(adj_X1_left) or src.find(adj_X1_left+' ') != -1:
            return None

        # If non-terminal X__1 occurs to the right of the current sub-phrase, rename X__1 to X__2 in
        # both source & target rules. In any synchronous rule, the source side will always have the
        # non-terminal X__2 following the X__1
        if src.startswith(sub_src+' ') or src.find(' '+sub_src+' ', 0, X1_indx) != -1:
            src = src.replace('X__1', 'X__2', 1)
            tgt = tgt.replace('X__1', 'X__2', 1)
            rep_str = 'X__1'
        else: rep_str = 'X__2'
    else:
        rep_str = 'X__1'

    s_side = replaceItem(src, sub_src, rep_str)
    t_side = replaceItem(tgt, sub_tgt, rep_str)

    # Constraint-5: Both sides have atleast one terminal aligned with each other
    tgtTermLst = t_side.split()
    aligned_terminal = False
    for pos in s_side.split():
        if not alignDoD.has_key(pos): continue
        for tgt_align_pos in alignDoD[pos].keys():
            try: 
                tgtTermLst.index(tgt_align_pos)
                aligned_terminal = True
                break
            except ValueError:
                pass

        # If all the constraints are satisfied compose the rule as a tuple and return it
        if aligned_terminal:
            return (s_side, t_side)

    return None
dataset/ETHPy150Open sfu-natlang/Kriya/src/Kriya-Grammar-Xtrctr/SCFGXtractor_ph1.py/checkConstraints/original