'A modified version of ``scan`` routine used in the relator-based
method of coset enumeration, described on pg. 162-163 [1], which
follows the idea that whenever the procedure is called and the scan
is incomplete then it makes new definitions to enable the scan to
complete; i.e it fills in the gaps in the scan of the relator or
subgroup generator.'

def scan_and_fill(self, alpha, word, max_cosets=coset_table_max_limit):

    A_dict = self.A_dict
    A_dict_inv = self.A_dict_inv
    table = self.table
    r = len(word)
    f = alpha
    i = 0
    b = alpha
    j = (r - 1)
    while True:
        while ((i <= j) and (table[f][A_dict[word[i]]] is not None)):
            f = table[f][A_dict[word[i]]]
            i += 1
        if (i > j):
            if (f != b):
                self.coincidence(f, b)
            return
        while ((j >= i) and (table[b][A_dict_inv[word[j]]] is not None)):
            b = table[b][A_dict_inv[word[j]]]
            j -= 1
        if (j < i):
            self.coincidence(f, b)
        elif (j == i):
            table[f][A_dict[word[i]]] = b
            table[b][A_dict_inv[word[i]]] = f
        else:
            self.define(f, word[i], max_cosets=max_cosets)
