<SYSTEM_TASK:>
Solve the following problem using Python, implementing the functions described below, one line at a time
<END_TASK>
<USER_TASK:>
Description:
 def find_shift_cc(im0, im1, ylim=None, xlim=None, subpix=True):
 """Finds the best shift between im0 and im1 using cross correlation Parameters im0: 2d array First image im1: 2d array Second image ylim: 2 numbers, optional The y limits of the search (if None full range is searched) xlim: 2 numbers, optional Ibidem with x Returns ------- [y, x]: 2 numbers The offset Notes ----- The origin of im1 in the im0 referential is returned ylim and xlim limit the possible output. No subpixel precision """

    # sanitize input
    im0 = np.asarray(im0, dtype=np.float32)
    im1 = np.asarray(im1, dtype=np.float32)
    # Remove mean
    im0 = im0 - np.nanmean(im0)
    im1 = im1 - np.nanmean(im1)
    # Save shapes as np array
    shape0 = np.asarray(im0.shape)
    shape1 = np.asarray(im1.shape)

    # Compute the offset and the pad (yleft,yright,xtop,xbottom)
    offset = 1 - shape1
    pad = np.lib.pad(-offset, (1, 1), mode='edge')

    # apply limit on padding
    if ylim is not None:
        pad[0] = -ylim[0]
        pad[1] = ylim[1] + (shape1 - shape0)[0]
    if xlim is not None:
        pad[2] = -xlim[0]
        pad[3] = xlim[1] + (shape1 - shape0)[1]

    # pad image
    im0, offset = pad_img(im0, pad)
    # compute Cross correlation matrix
    xc = cv2.matchTemplate(im0, im1, cv2.TM_CCORR)
    # Find maximum of abs (can be anticorrelated)
    idx = np.asarray(np.unravel_index(np.argmax(xc), xc.shape))
    # Return origin in im0 units
    if subpix:
        # update idx
        idx = np.asarray([get_peak_pos(xc[:, idx[1]], wrap=False),
                          get_peak_pos(xc[idx[0], :], wrap=False)])
    else:
        # restrics to reasonable values
        idx[idx > shape // 2] -= shape[idx > shape // 2]
        
    return idx + offset