def add_it_prism(coords, rel, items, mod, annotations): """ This func. adds item and returns the new model (mod). The first test detects 'in same place' and item is added to whatever is at coords. Second test detects when coords are outside, then list of new_dims + new_orig is used to copy mod to new mod. item is added to this, having changed coords by adding new_orig to them. Third test: used to check if mod[coords], i.e. cell at current coords, is empty. In this case, item is added. Finally, where cells already has item, update coords according to rel and try again. As it is recursive and may increase co-ords, it needs to expand array sometimes. """ item, item_in_mod = items if rel == (0, 0, 0): # Get what is currently present in mod at coordinates coords. current = mod.get(coords) # Concatenate item to what is already present at the given # coordinates in mod (item and current are strings). item = item + current if current is not None else item mod[coords] = item return mod, annotations dims_mod = spatial_array.dimensions(mod) # If coords is not within dims_mod, adjust origin and coords suitably. # outside returns ((new_coords),(new_origin)) = newlis newlis = utilities.outside(coords, dims_mod) if newlis is not None: # Expand mod by making space for an extra item mod = spatial_array.copy_array(mod, {}, newlis[0], newlis[1]) # New origin, so old coords have to be updated new_coords = utilities.list_add(coords, newlis[1]) items = (item, item_in_mod) return add_it_prism(new_coords, rel, items, mod, annotations) # Reaches here when coords is within dims, rel != 0,0,0 and # mod[coords] has space (is None) for a new item, which can be inserted. if mod.get(coords) is None: # An annotation is necessary only in the special case where the already # -present item is the 2nd element (LO) of some annotation AND we # are moving in the same direction as rel. In this case, we add # the annotation: [rel, item, item_in_mod] new_annotation = subj_or_obj_in_annotations(annotations, item, rel, item_in_mod) if new_annotation is not None: annotations.append(new_annotation) mod[coords] = item return mod, annotations # If there is another item at mod[coords], move further along the # direction specified by rel, and try to add item there. # Find the coords of the token already present in the model (this might be # the subject or the object. Remember, coords has already been updated in # add_item. We don't need to reverse this update. # Whether it's add subj or add obj, rel will be the same (as add_obj gets # the negation of rel. The new item is somewhere to the rel of item_in_mod # The ref obj always goes at the end of the annotation new_annotation = [rel, item, item_in_mod] if new_annotation not in annotations: annotations.append(new_annotation) # Continue as per fff strategy and add the token. updated_coords = utilities.update_coords(coords, rel) items = (item, item_in_mod) return add_it_prism(updated_coords, rel, items, mod, annotations)
def loop_throught_intnesionalrepr(self, grouped_list, rel_to_move, move_tokens_coordinates, mod): """ Loops through intensional representations of premises and compares tokens to the intermediate object or located object based on the parameters passed, and adds to the move_token_coordinates dictionary, which it returns. ARGUMENTS: grouped_list: list of objects which have already been grouped, this is used to group the next suitable object which is reached from one of the grouped objects in the correct direction (not same dir as rel_to_move) rel_to_move: direction from ref to int to loc object""" # Last intensional representation is the verification/generation # premise (conclusion) for representation in self.intensionalrepr[:-1]: # Get groups of tokens by checking movement in dirs # other than that between the loc.obj, int.obj and ref.obj # (done using not same_dir_movement). # Find if current object is in subj or obj position in # the prems. Eg. representation[1] = ['[]'], [1][0] = '[]' if representation[1][0] in grouped_list and \ not utilities.same_dir_movement(rel_to_move, representation[0]): # intermediate_obj is the subject in prop, we need # to move in neg(rel) from subj to obj cur_object = representation[2][0] grouped_list.append(cur_object) cur_coords = utilities.get_coordinates_from_token( cur_object, mod) curobj_new_coords = utilities.list_add(cur_coords, rel_to_move) move_tokens_coordinates[cur_object] = curobj_new_coords elif representation[2][0] in grouped_list and \ not utilities.same_dir_movement(rel_to_move, representation[0]): # intermediate obj is the object in prop, we need # to move in rel from obj to subj cur_object = representation[1][0] grouped_list.append(cur_object) cur_coords = utilities.get_coordinates_from_token( cur_object, mod) curobj_new_coords = utilities.list_add(cur_coords, rel_to_move) move_tokens_coordinates[cur_object] = curobj_new_coords return move_tokens_coordinates
def newds(oldarr, dlists): """ Uses dims of oldarr and rows/cols/planes to slice empty rows/cols/ planes based on dlists, and get the dimensions of a new array. Finally it creates the new array. If dlists is [[],[],[]], i.e. no values for rows, cols, planes to eliminate, it returns oldarr. """ old_dims = utilities.list_add(dimensions(oldarr), (1, 1, 1)) # Get the newdims: oldarr dim - corresponding dlist dim new_dims = [] for i, old_dim in enumerate(old_dims): new_dims.append(old_dim - len(dlists[i])) new_arr = make_array(new_dims) return new_arr
def combine(rel, subj_coords, obj_coords, subj_mod, obj_mod): """ This func. combines subj_mod and obj_mod in a way that satisfies rel.""" # Get the dimensions of subj_mod and obj_mod, we need to add # (1, 1, 1) as the dimensions function returns 0-indexed dims. subj_dims = utilities.list_add(spatial_array.dimensions(subj_mod), (1, 1, 1)) obj_dims = utilities.list_add(spatial_array.dimensions(obj_mod), (1, 1, 1)) # dims origins will return a 3-tuple: new dims, new origin for # subj_mod and new origin for obj_mod tmp = spatial_array.dims_origins(rel, subj_dims, obj_dims, subj_coords, obj_coords) new_dims, new_subj_orig, new_obj_orig = tmp # The call to copy_array with subj_mod as inarr creates an outarr # of desired dimensions, and then inserts the values in inarr at the # correct positions in the new outarr through the copy_arr function. outarr = spatial_array.copy_array(subj_mod, {}, new_dims, new_subj_orig) # The call to copy_array with obj_mod doesn't need to create a new # array, it uses the array produced by the previous call with subj_mod # (which already has the correct dims). So this only inserts values # in outarr from inarr through the copy_arr function. outarr = spatial_array.copy_array(obj_mod, outarr, new_dims, new_obj_orig) return outarr
def verify(rel, subj_coords, obj_coords, mod): """ It returns mod if rel holds between subj_coords and obj_coords in mod (i.e. subj_coord can be reached by adding rel to obj_coord a certain number of times). Otherwise, it returns None. """ obj_coords = utilities.list_add(rel, obj_coords) dims_mod = spatial_array.dimensions(mod) if utilities.outside(obj_coords, dims_mod) is not None: # obj_coords is outside dims_mod, this might occur, for e.g., # when addition of rel to obj_mod has caused it to become # more extreme than subj_mod (and dims). return None if subj_coords == obj_coords: # If obj reaches subj after a certain no. of steps return mod # Recursive call with new obj_coords return verify(rel, subj_coords, obj_coords, mod)
def add_item(coords, rel, item, mod): """ This function updates coordinates (coords) according to rel and then calls add_it. It checks if coordinates are outside the model, and if so, expands mod. This is necessary in case rel is (0, 0, 0), but assigned coords are outside. """ coords = utilities.update_coords(coords, rel) # Dimensions: 0-based. dims_mod = spatial_array.dimensions(mod) # Check if new token will fit into the existing array, or if it needs # expansion. If it needs expansion, get the new dimensions & new origin. # newlis = (newdims, neworigin) newlis = utilities.outside(coords, dims_mod) if rel == (0, 0, 0) and newlis is not None: mod = spatial_array.copy_array(mod, {}, newlis[0], newlis[1]) coords = utilities.list_add(coords, newlis[1]) return add_it(coords, rel, item, mod)
def recursive_copy(inarr, outarr, dims, new_origin): """ Recursive function. Called by copy_array, it changes outarr destructively, it doesn't return anything. It can copy inarr into outarr at either new_origin, or at (0, 0, 0). Dims are dimensions of inarr, and may be smaller than those of outarr.""" pos = utilities.find_index_neg_num(dims) # If there are no negative no.s in dims if pos is None: # Insert value in inarr into outarr at coords dims + new_origin item = inarr.get(dims) out_dims = utilities.list_add(dims, new_origin) outarr[out_dims] = item tmp_dims = tuple((v - 1 if i == 0 else v for i, v in enumerate(dims))) recursive_copy(inarr, outarr, tmp_dims, new_origin) # There are negative no.s in dims: elif pos < (len(dims) - 1): tmp_dims = update(pos, dims, dimensions(inarr)) recursive_copy(inarr, outarr, tmp_dims, new_origin)
def add_it(coords, rel, item, mod): """ This func. adds item and returns the new model (mod). The first test detects 'in same place' and item is added to whatever is at coords. Second test detects when coords are outside, then list of new_dims + new_orig is used to copy mod to new mod. item is added to this, having changed coords by adding new_orig to them. Third test: used to check if mod[coords], i.e. cell at current coords, is empty. In this case, item is added. Finally, where cells already has item, update coords according to rel and try again. As it is recursive and may increase co-ords, it needs to expand array sometimes. """ if rel == (0, 0, 0): # Get what is currently present in mod at coordinates coords. current = mod.get(coords) # Concatenate item to what is already present at the given # coordinates in mod (item and current are strings). item = item + current if current is not None else item mod[coords] = item return mod dims_mod = spatial_array.dimensions(mod) # If coords is not within dims_mod, adjust origin and coords suitably. # outside returns ((new_coords),(new_origin)) = newlis newlis = utilities.outside(coords, dims_mod) if newlis is not None: # Expand mod by making space for an extra item mod = spatial_array.copy_array(mod, {}, newlis[0], newlis[1]) # New origin, so old coords have to be updated new_coords = utilities.list_add(coords, newlis[1]) return add_it(new_coords, rel, item, mod) # Reaches here when coords is within dims, rel != 0,0,0 and # mod[coords]has space (is None) for a new item, which can be inserted. if mod.get(coords) is None: mod[coords] = item return mod # If there is another item at mod[coords], move further along the # direction specified by rel, and try to add item there. updated_coords = utilities.update_coords(coords, rel) return add_it(updated_coords, rel, item, mod)