コード例 #1
0
def Q1E_report(train_images, train_labels, test_images, test_labels,
               theta_map):
    #average for train
    log_likelihood_train = find_log_likelihood(train_images, theta_map, 1 / 10)
    avg_likelihood_train = avg_likelihood(train_images, train_labels,
                                          log_likelihood_train)
    print("Avg train log likelihood ", avg_likelihood_train)

    #average for test
    log_likelihood_test = find_log_likelihood(test_images, theta_map, 1 / 10)
    avg_likelihood_test = avg_likelihood(test_images, test_labels,
                                         log_likelihood_test)
    print("Avg test log likelihood ", avg_likelihood_test)

    #predictions for train
    predict_train = predict(train_images, theta_map, log_likelihood_train)
    total_correct_train = np.sum(
        np.nonzero(predict_train)[1] == np.nonzero(train_labels)
        [1])  #get total number of correct predictions
    accuracy_train = total_correct_train / float(
        train_labels.shape[0])  #get accuracy
    print('Train Accuracy ', accuracy_train)

    #predictions for test
    predict_test = predict(test_images, theta_map, log_likelihood_test)
    total_correct_test = np.sum(
        np.nonzero(predict_test)[1] == np.nonzero(test_labels)
        [1])  #get total number of correct predictions
    accuracy_test = total_correct_test / float(
        test_labels.shape[0])  #get accuracy
    print('Test Accuracy ', accuracy_test)
コード例 #2
0
ファイル: a3starter.py プロジェクト: vibe95/Digit-recognition
def Q3D_report(train_images, train_labels, test_images, test_labels, w):
    #average for train
    avg_likelihood_train = avg_pred_log(w, train_images)
    print("Avg train log likelihood ", avg_likelihood_train)

    #average for test
    avg_likelihood_test = avg_pred_log(w, test_images)
    print("Avg test log likelihood ", avg_likelihood_test)

    #predictions for train
    predict_train = predict_regression(train_images, w)
    total_correct_train = np.sum(
        np.nonzero(predict_train)[1] == np.nonzero(train_labels)
        [1])  #get total number of correct predictions
    accuracy_train = total_correct_train / float(
        train_labels.shape[0])  #get accuracy
    print('Train Accuracy ', accuracy_train)

    #predictions for test
    predict_test = predict_regression(test_images, w)
    total_correct_test = np.sum(
        np.nonzero(predict_test)[1] == np.nonzero(test_labels)
        [1])  #get total number of correct predictions
    accuracy_test = total_correct_test / float(
        test_labels.shape[0])  #get accuracy
    print('Test Accuracy ', accuracy_test)
コード例 #3
0
ファイル: mesh_traversal.py プロジェクト: twbabyduck/mesh_CNN
    def get_neighs(vertex, r):
        verts = list()

        # level_0
        verts.append(vertex)
        v = vertex

        # find closest point in level 1
        if sparse.issparse(adj_mtx):
            nz = adj_mtx.tolil().rows
            ix_list = nz[v]
        else:
            row = adj_mtx[v]
            ix_list = np.nonzero(row)
            ix_list = ix_list[0]

        dists = []
        for j in ix_list:
            d = get_dist(coords, v, j)
            dists.append(d)
        ix_min = ix_list[dists.index(min(dists))]
        closest_ix = ix_min

        # levels_>=1
        for i in range(1, r + 1):
            # this is the closest vertex of the new level
            # find the ordering of the level
            arr = get_order(adj_mtx, coords, ix_list, closest_ix, verts)
            verts = verts + arr
            # get next level: for each in ix_list, get neighbors that are not in <verts>, then add them to the new list
            next_list = []
            for j in ix_list:
                if sparse.issparse(adj_mtx):
                    new_row = nz[j]
                else:
                    new_row = adj_mtx[j]
                    new_row = np.nonzero(new_row)
                    new_row = new_row[0]

                for k in new_row:
                    if k not in verts:
                        next_list.append(k)
            next_list = list(set(next_list))

            # find starting point of next level using line eq
            c1 = coords[vertex]
            c2 = coords[closest_ix]
            line_dists = []
            for j in next_list:
                c3 = coords[j]
                line_dist = LA.norm(np.cross(c2 - c1, c1 - c3)) / LA.norm(
                    c2 - c1)  # calculate distance to line
                line_dists.append(line_dist)
            ix_list = next_list
            closest_ix = next_list[line_dists.index(min(line_dists))]
        return verts
コード例 #4
0
def aveFreqDomain(X, SR):

    #X = zoInterp(X,2);
    x_new = np.tile(x, (numInterp, 1))
    X = reshape(x_new, (1, []))
    L = X.size
    Y = np.fft(X)
    P2 = np.abs(Y / L)
    P1 = P2[0:L / 2 + 1]
    P1[1:-1] = 2 * P1[1:-1]
    f = SR * np.arange(L / 2) / L

    y = np.zeros((1, 5))
    begin = []
    stop = []
    for i in np.arange(5):
        if i == 1:
            begin = np.nonzero(np.floor(f) == 5)
            begin = begin[0]
            stop = np.nonzero(np.floor(f) == 15)
            stop = stop[0]
            y[0] = np.mean(P1[begin:stop + 1])
        elif i == 2:
            begin = np.nonzero(np.floor(f) == 20)
            begin = begin[0]
            stop = np.nonzero(np.floor(f) == 25)
            stop = stop[0]
            y[1] = np.mean(P1[begin:stop + 1])
        elif i == 3:
            begin = np.nonzero(np.floor(f) == 75)
            begin = begin[0]
            stop = np.nonzero(np.floor(f) == 115)
            stop = stop[0]
            y(3) = np.mean(P1[begin:stop + 1])
        elif i == 4:
            begin = np.nonzero(np.floor(f) == 125)
            begin = begin[0]
            stop = np.nonzero(np.floor(f) == 160)
            stop = stop[0]
            y(4) = np.mean(P1[begin:stop + 1])
        elif i == 5:
            begin = np.nonzero(np.floor(f) == 160)
            begin = begin[0]
            stop = np.nonzero(np.floor(f) == 175)
            stop = stop[0]
            y(5) = np.mean(P1[begin:stop + 1])

    return y
コード例 #5
0
    def loss_augmented_inference(self, x, y, w, relaxed=False, return_energy=False):
        """Loss-augmented Inference for x relative to y using parameters w.

        Finds (approximately)
        argmax_y_hat np.dot(w, joint_feature(x, y_hat)) + loss(y, y_hat)
        using self.inference_method.
        """
        self.inference_calls += 1
        self._check_size_w(w)  # check if size of w is equal to size of joint feature
        # need to compute the joint feature and hinge loss
        # return self.loss_augmented_inference_graph_iht(x, y, w, relaxed=relaxed)

        # y_hat = x
        # y_hat = np.random.rand(len(y))
        y_hat = np.zeros_like(y)
        yt = np.copy(y_hat)
        max_iter = 1000
        for iter in range(max_iter):
            print("iter {}".format(iter))
            print("yt {}\n{}".format(yt, np.nonzero(yt)))
            y_prev = np.copy(yt)
            gradient = self._get_cost_augment_grad(x, y, w, yt)
            print("gradient {}".format(gradient))

            yt = yt + 0.001 * gradient
            yt[yt <= 0.] = 0.
            yt[yt >= 1.0] = 1.0
            gap_y = np.linalg.norm(yt - y_prev) ** 2
            if gap_y < 1e-6:
                break
        return yt
コード例 #6
0
ファイル: main.py プロジェクト: zhyb86/autorustler
def test_PhotometricError(iref, inew, R, T, points, D):
    h = 1e-7
    hh = 1.0 / h
    E0, g0 = PhotometricError(iref, inew, R, T, points, D)
    Erx, Ery, Erz = 0, 0, 0
    Erx = hh * (PhotometricError(iref, inew, R + np.array([h, 0, 0]), T,
                                 points, D)[0] - E0)
    Ery = hh * (PhotometricError(iref, inew, R + np.array([0, h, 0]), T,
                                 points, D)[0] - E0)
    Erz = hh * (PhotometricError(iref, inew, R + np.array([0, 0, h]), T,
                                 points, D)[0] - E0)

    Etx = hh * (PhotometricError(iref, inew, R, T + np.array([h, 0, 0]),
                                 points, D)[0] - E0)
    Ety = hh * (PhotometricError(iref, inew, R, T + np.array([0, h, 0]),
                                 points, D)[0] - E0)
    Etz = hh * (PhotometricError(iref, inew, R, T + np.array([0, 0, h]),
                                 points, D)[0] - E0)

    n = np.nonzero(g0[6:])[0][0]
    print 'nonzero point', n
    D[n] += h
    Ed = hh * (PhotometricError(iref, inew, R, T, points, D)[0] - E0)

    print 'E', E0, 'g:', g0[:7]
    print 'numerical gR: (%f %f %f)' % (Erx, Ery, Erz)
    print 'numerical gT: (%f %f %f)' % (Etx, Ety, Etz)
    print 'numerical D: %f' % Ed
    print 'Error_R: (%f %f %f)' % (Erx - g0[0], Ery - g0[1], Erz - g0[2])
    print 'Error_T: (%f %f %f)' % (Etx - g0[3], Ety - g0[4], Etz - g0[5])
    print 'Error_D:', (Ed - g0[6 + n])
コード例 #7
0
def param_to_tree(param, sparse_info, single_tree):
    # we want to iterate over model info and replace it so that we have something that can be compared
    # this only works for binary class for now
    # this is due to laziness, and difficulty to compare multiclass?
    coef, inter, leaf = param
    thresholds = (-inter / coef).tolist()
    leaves = (leaf).tolist()
    tree = copy.deepcopy(single_tree)

    # now figure out the columns
    feat_splits = []
    for col_idx in range(sparse_info.shape[1]):
        split_indx = np.nonzero(sparse_info[:, col_idx])[0].tolist()[0]
        feat_splits.append(split_indx)

    # now combine it all based on model_info...
    for idx, threshold in enumerate(thresholds):
        # iterate through the tree and replace where
        # split_index == idx
        tree = update_tree_info(tree.copy(), idx, threshold, feat_splits[idx])

    for idx, value in enumerate(leaves):
        # iterate through the tree and replace where
        # split_index == idx
        tree = update_leaf_info(tree.copy(), idx, value)
    return tree
コード例 #8
0
ファイル: main.py プロジェクト: UIKit0/autorustler
def test_PhotometricError(iref, inew, R, T, points, D):
    h = 1e-7
    hh = 1.0 / h
    E0, g0 = PhotometricError(iref, inew, R, T, points, D)
    Erx, Ery, Erz = 0, 0, 0
    Erx = hh * (PhotometricError(
        iref, inew, R + np.array([h, 0, 0]), T, points, D)[0] - E0)
    Ery = hh * (PhotometricError(
        iref, inew, R + np.array([0, h, 0]), T, points, D)[0] - E0)
    Erz = hh * (PhotometricError(
        iref, inew, R + np.array([0, 0, h]), T, points, D)[0] - E0)

    Etx = hh * (PhotometricError(
        iref, inew, R, T + np.array([h, 0, 0]), points, D)[0] - E0)
    Ety = hh * (PhotometricError(
        iref, inew, R, T + np.array([0, h, 0]), points, D)[0] - E0)
    Etz = hh * (PhotometricError(
        iref, inew, R, T + np.array([0, 0, h]), points, D)[0] - E0)

    n = np.nonzero(g0[6:])[0][0]
    print 'nonzero point', n
    D[n] += h
    Ed = hh * (PhotometricError(iref, inew, R, T, points, D)[0] - E0)

    print 'E', E0, 'g:', g0[:7]
    print 'numerical gR: (%f %f %f)' % (Erx, Ery, Erz)
    print 'numerical gT: (%f %f %f)' % (Etx, Ety, Etz)
    print 'numerical D: %f' % Ed
    print 'Error_R: (%f %f %f)' % (Erx - g0[0], Ery - g0[1], Erz - g0[2])
    print 'Error_T: (%f %f %f)' % (Etx - g0[3], Ety - g0[4], Etz - g0[5])
    print 'Error_D:', (Ed - g0[6 + n])
コード例 #9
0
    def cost(self, controls, states, system_eval_step):
        """
        Compute the penalty.

        Arguments:
        controls
        states
        system_eval_step

        Returns:
        cost
        """
        cost = 0
        # Iterate over the controls, penalize each control that has
        # frequencies greater than its maximum frequency.
        for i, max_bandwidth in enumerate(self.max_bandwidths):
            control_fft = anp.fft.fft(controls[:, i])
            control_fft_sq = anp.abs(control_fft)
            penalty_freq_indices = anp.nonzero(self.freqs >= max_bandwidth)[0]
            penalized_ffts = control_fft_sq[penalty_freq_indices]
            penalty = anp.sum(penalized_ffts)
            penalty_normalized = penalty / (penalty_freq_indices.shape[0] *
                                            anp.max(penalized_ffts))
            cost = cost + penalty_normalized
        cost_normalized = cost / self.control_count

        return cost_normalized * self.cost_multiplier
コード例 #10
0
    def _calculate_observables(self, state):

        # Note that this is very different from the original paper, which uses an observation model tailored to the
        # collected data

        # Proportion of individuals with the most common strain (Numminem cross-check)
        strain_observations = np.sum(state, axis=0)
        most_common_strain = np.argmax(strain_observations)
        prevalence_most_common_strain = np.sum(state[:, most_common_strain],
                                               dtype=np.float) / float(
                                                   self.n_individuals)

        # Number of singleton strains (= only on 1 individual, Numminem cross-check)
        n_singleton_strains = np.sum(strain_observations == 1)

        # Number of observed strains (Numminen 2)
        n_observed_strains = len(
            strain_observations[np.nonzero(strain_observations)])

        # Shannon entropy of observed strain distribution (Numminen 1)
        p_observed_strains = strain_observations[np.nonzero(
            strain_observations)]  # Remove zeros
        p_observed_strains = p_observed_strains.astype(np.float) / float(
            np.sum(p_observed_strains))  # Normalize
        shannon_entropy = -np.sum(
            p_observed_strains * np.log(p_observed_strains))

        # Any / multiple infections of individuals
        any_infection = (np.sum(state, axis=1) > 0)
        multiple_infections = (np.sum(state, axis=1) > 1)

        # Prevalence of any infection (Numminen 3)
        prevalence_any = np.sum(any_infection,
                                dtype=np.float) / self.n_individuals

        # Prevalence of multiple infections (Numminen 4)
        prevalence_multiple = np.sum(multiple_infections,
                                     dtype=np.float) / self.n_individuals

        # Combine summary statistics
        summary_statistics = np.array([
            shannon_entropy, n_observed_strains, prevalence_any,
            prevalence_multiple, prevalence_most_common_strain,
            n_singleton_strains
        ])

        return summary_statistics
コード例 #11
0
ファイル: node.py プロジェクト: wpfhtl/ddn
 def _get_nu_star(self, x, y):
     """Compute nu_star if not provided by the problem's solver."""
     if np.all(np.abs(self.fY(x, y)) < self.eps):
         return np.nan # flag that unconstrained gradient should be used
     indx = np.nonzero(self.hY(x, y))
     if len(indx[0]) == 0:
         return 0.0 # still use constrained gradient
     return self.fY(x, y)[indx[0][0]] / self.hY(x, y)[indx[0][0]]
コード例 #12
0
ファイル: main.py プロジェクト: UIKit0/autorustler
def PhotometricError(iref, inew, R, T, points, D):
    # points is a tuple ([y], [x]); convert to homogeneous
    siz = iref.shape
    npoints = len(points[0])
    f = siz[1]  # focal length, FIXME
    Xref = np.vstack(((points[1] - siz[1]*0.5) / f,  # x
                      (siz[0]*0.5 - points[0]) / f,  # y (left->right hand)
                      np.ones(npoints)))             # z = 1
    # this is confusingly written -- i am broadcasting the translation T to
    # every column, but numpy broadcasting only works if it's rows, hence all
    # the transposes
    # print D * Xref
    Xnew = (np.dot(so3.exp(R), (D * Xref)).T + T).T
    # print Xnew
    # right -> left hand projection
    proj = Xnew[0:2] / Xnew[2]
    p = (-proj[1]*f + siz[0]*0.5, proj[0]*f + siz[1]*0.5)
    margin = 10  # int(siz[0] / 5)
    inwindow_mask = ((p[0] >= margin) & (p[0] < siz[0]-margin-1) &
                     (p[1] >= margin) & (p[1] < siz[1]-margin-1))
    npts_inw = sum(inwindow_mask)
    if npts_inw < 10:
        return 1e6, np.zeros(6 + npoints)
    # todo: filter points which are now out of the window
    oldpointidxs = (points[0][inwindow_mask],
                    points[1][inwindow_mask])
    newpointidxs = (p[0][inwindow_mask], p[1][inwindow_mask])
    origpointidxs = np.nonzero(inwindow_mask)[0]
    E = InterpolatedValues(inew, newpointidxs) - iref[oldpointidxs]
    # dE/dk ->
    # d/dk r_p^2 = d/dk (Inew(w(r, T, D, p)) - Iref(p))^2
    # = -2r_p dInew/dp dp/dw dw/dX dX/dk
    # = -2r_p * g(w(r, T, D, p)) * dw(r, T, D, p)
    # intensity gradients for each point
    Ig = InterpolatedGradients(inew, newpointidxs)
    # TODO: use tensors for this
    # gradients for R, T, and D
    gradient = np.zeros(6 + npoints)
    for i in range(npts_inw):
        # print 'newidx (y,x) = ', newpointidxs[0][i], newpointidxs[1][i]
        # Jacobian of w
        oi = origpointidxs[i]
        Jw = dw(Xref[0][oi], Xref[1][oi], D[oi], R, T)
        # scale back up into pixel space, right->left hand coords to get
        # Jacobian of p
        Jp = f * np.vstack((-Jw[1], Jw[0]))
        # print origpointidxs[i], 'Xref', Xref[:, i], 'Ig', Ig[:, i], \
        #     'dwdRz', Jw[:, 2], 'dpdRz', Jp[:, 2]
        # full Jacobian = 2*E + Ig * Jp
        J = np.sign(E[i]) * np.dot(Ig[:, i], Jp)
        # print '2 E[i]', 2*E[i], 'Ig*Jp', np.dot(Ig[:, i], Jp)
        gradient[:6] += J[:6]
        # print J[:6]
        gradient[6+origpointidxs[i]] += J[6]

    print R, T, np.sum(np.abs(E)), npts_inw
    # return ((0.2*(npoints - npts_inw) + np.dot(E, E)), gradient)
    return np.sum(np.abs(E)) / (npts_inw), gradient / (npts_inw)
コード例 #13
0
ファイル: main.py プロジェクト: zhyb86/autorustler
def PhotometricError(iref, inew, R, T, points, D):
    # points is a tuple ([y], [x]); convert to homogeneous
    siz = iref.shape
    npoints = len(points[0])
    f = siz[1]  # focal length, FIXME
    Xref = np.vstack((
        (points[1] - siz[1] * 0.5) / f,  # x
        (siz[0] * 0.5 - points[0]) / f,  # y (left->right hand)
        np.ones(npoints)))  # z = 1
    # this is confusingly written -- i am broadcasting the translation T to
    # every column, but numpy broadcasting only works if it's rows, hence all
    # the transposes
    # print D * Xref
    Xnew = (np.dot(so3.exp(R), (D * Xref)).T + T).T
    # print Xnew
    # right -> left hand projection
    proj = Xnew[0:2] / Xnew[2]
    p = (-proj[1] * f + siz[0] * 0.5, proj[0] * f + siz[1] * 0.5)
    margin = 10  # int(siz[0] / 5)
    inwindow_mask = ((p[0] >= margin) & (p[0] < siz[0] - margin - 1) &
                     (p[1] >= margin) & (p[1] < siz[1] - margin - 1))
    npts_inw = sum(inwindow_mask)
    if npts_inw < 10:
        return 1e6, np.zeros(6 + npoints)
    # todo: filter points which are now out of the window
    oldpointidxs = (points[0][inwindow_mask], points[1][inwindow_mask])
    newpointidxs = (p[0][inwindow_mask], p[1][inwindow_mask])
    origpointidxs = np.nonzero(inwindow_mask)[0]
    E = InterpolatedValues(inew, newpointidxs) - iref[oldpointidxs]
    # dE/dk ->
    # d/dk r_p^2 = d/dk (Inew(w(r, T, D, p)) - Iref(p))^2
    # = -2r_p dInew/dp dp/dw dw/dX dX/dk
    # = -2r_p * g(w(r, T, D, p)) * dw(r, T, D, p)
    # intensity gradients for each point
    Ig = InterpolatedGradients(inew, newpointidxs)
    # TODO: use tensors for this
    # gradients for R, T, and D
    gradient = np.zeros(6 + npoints)
    for i in range(npts_inw):
        # print 'newidx (y,x) = ', newpointidxs[0][i], newpointidxs[1][i]
        # Jacobian of w
        oi = origpointidxs[i]
        Jw = dw(Xref[0][oi], Xref[1][oi], D[oi], R, T)
        # scale back up into pixel space, right->left hand coords to get
        # Jacobian of p
        Jp = f * np.vstack((-Jw[1], Jw[0]))
        # print origpointidxs[i], 'Xref', Xref[:, i], 'Ig', Ig[:, i], \
        #     'dwdRz', Jw[:, 2], 'dpdRz', Jp[:, 2]
        # full Jacobian = 2*E + Ig * Jp
        J = np.sign(E[i]) * np.dot(Ig[:, i], Jp)
        # print '2 E[i]', 2*E[i], 'Ig*Jp', np.dot(Ig[:, i], Jp)
        gradient[:6] += J[:6]
        # print J[:6]
        gradient[6 + origpointidxs[i]] += J[6]

    print R, T, np.sum(np.abs(E)), npts_inw
    # return ((0.2*(npoints - npts_inw) + np.dot(E, E)), gradient)
    return np.sum(np.abs(E)) / (npts_inw), gradient / (npts_inw)
コード例 #14
0
def normalise_points(pts):
    """
    Function translates and normalises a set of 2D or 3d homogeneous points
    so that their centroid is at the origin and their mean distance from
    the origin is sqrt(2).  This process typically improves the
    conditioning of any equations used to solve homographies, fundamental
    matrices etc.


    Inputs:
    pts: 3xN array of 2D homogeneous coordinates

    Returns:
    newpts: 3xN array of transformed 2D homogeneous coordinates.  The
            scaling parameter is normalised to 1 unless the point is at
            infinity.
    T: The 3x3 transformation matrix, newpts = T*pts
    """
    if pts.shape[0] == 4:
        pts = hom_3d_to_2d(pts)

    if pts.shape[0] != 3 and pts.shape[0] != 4  :
        print "Shape error"


    finiteind = np.nonzero(abs(pts[2,:]) > np.spacing(1))

    if len(finiteind[0]) != pts.shape[1]:
        print('Some points are at infinity')

    dist = []
    pts = pts/pts[2,:]
    for i in finiteind:
        #Replaced below for autograd
#        pts[0,i] = pts[0,i]/pts[2,i]
#        pts[1,i] = pts[1,i]/pts[2,i]
#        pts[2,i] = 1;

        c = np.mean(pts[0:2,i].T, axis=0).T

        newp1 = pts[0,i]-c[0]
        newp2 = pts[1,i]-c[1]

        dist.append(np.sqrt(newp1**2 + newp2**2))

    dist = np.array(dist)

    meandist = np.mean(dist)

    scale = np.sqrt(2)/meandist

    T = np.array([[scale, 0, -scale*c[0]], [0, scale, -scale*c[1]], [0, 0, 1]])

    newpts = np.dot(T,pts)


    return newpts, T
コード例 #15
0
def get_orthogonality_score(C_matrix, verbose=True):
    """
    Gets the angle between each subspace and the other ones.

    Note the we leave the diagonal as zeros, because the angles are 1 anyway
    And it helps to have a more representative mean.
    """

    in_degree = True

    len_1, len_2 = C_matrix.shape
    orthogonality_matrix = np.zeros((len_2, len_2))

    for lat_i in range(0, len_2):
        for lat_j in range(lat_i + 1, len_2):
            angle = np.dot(C_matrix[:, lat_i], C_matrix[:, lat_j]) / (np.dot(
                np.linalg.norm(C_matrix[:, lat_i]),
                np.linalg.norm(C_matrix[:, lat_j])))
            orthogonality_matrix[lat_i, lat_j] = np.arccos(np.abs(angle))
            orthogonality_matrix[lat_j, lat_i] = np.arccos(np.abs(angle))

    if in_degree:
        orthogonality_matrix = 180 * orthogonality_matrix / np.pi

    mean_per_sub_space = np.sum(np.abs(orthogonality_matrix), 1) / (len_2 - 1)

    glob_mean = np.mean(mean_per_sub_space)

    try:
        all_non_diag = orthogonality_matrix.flatten()
        all_non_diag = all_non_diag[np.nonzero(all_non_diag)]

        tenth_percentil = np.percentile(all_non_diag, 25)
        ninetith_percentil = np.percentile(all_non_diag, 75)

        small_avr = np.average(
            all_non_diag,
            weights=(all_non_diag <= tenth_percentil).astype(int))
        high_avr = np.average(
            all_non_diag,
            weights=(all_non_diag >= ninetith_percentil).astype(int))
    except:
        small_avr = glob_mean
        high_avr = glob_mean

    if verbose:
        print(np.around(orthogonality_matrix, 2))
        print("Mean abs angle per subspace: ", mean_per_sub_space)
        print("Mean abs angle overall: ", glob_mean)
        #print("Std abs angle overall: ", np.std(mean_per_sub_space))

    # print(small_avr, high_avr)
    if len_2 <= 1:
        glob_mean = small_avr = high_avr = 0

    return glob_mean, small_avr, high_avr
コード例 #16
0
def map_to_index_set(_map, threshold=0.9, max_set_size=K):
    thresholded_map = np.where(_map > threshold, _map, 0.0)
    map_diagonal = np.diag(thresholded_map)
    assert np.array_equal(np.diag(map_diagonal), thresholded_map)

    nonzeros = np.nonzero(map_diagonal)[0]
    assert len(nonzeros) <= max_set_size

    index_set = tuple(nonzeros)
    return index_set
コード例 #17
0
def lossfunction_all(rating_matrix, movie_vectors, user_vectors, flag):
    if flag == 1:  # used in user tree construction, user_vectors is a 1*K vector
        user_vectors = np.array(
            [user_vectors for i in range(len(rating_matrix))])
    if flag == 0:  # used in item tree construction, movie_vectors is a 1*K vector
        movie_vectors = np.array(
            [movie_vectors for i in range(rating_matrix.shape[1])])
    value = 0
    # Add regularization term
    user_l = user_vectors[np.nonzero(user_vectors)]
    value = value + lmd_u * np.dot(user_l, user_l)
    mov_l = movie_vectors[np.nonzero(movie_vectors)]
    value = value + lmd_v * np.dot(mov_l, mov_l)

    if len(rating_matrix) == 0:
        return value

    predict = np.dot(user_vectors, movie_vectors.T)
    P = predict[np.nonzero(rating_matrix)]
    R = rating_matrix[np.nonzero(rating_matrix)]
    Err = P - R
    value = value + np.dot(Err, Err)

    np.random.seed(0)
    num_pair = 20
    num_user, num_item = rating_matrix.shape
    for i in range(num_pair):
        c1, c2 = np.random.randint(0, num_item * num_user, 2)
        u1, i1 = c1 // num_item, c1 % num_item
        u2, i2 = c2 // num_item, c2 % num_item
        if rating_matrix[u1][i1] > rating_matrix[u2][i2]:
            diff = np.dot(user_vectors[u1, :].T,
                          movie_vectors[i1, :]) - np.dot(
                              user_vectors[u2, :].T, movie_vectors[i2, :])
            diff = -diff
            value = value + lmd_BPR * np.log(1 + np.exp(diff))

    return value
コード例 #18
0
def normalise_points_RadiusScale(pts, radius):
    """
  Function translates and normalises a set of 2D or 3d homogeneous points
  so that their centroid is at the origin
  Add radius(distance between camera and marker) as one influenced factor of Scale
  This process typically improves the
  conditioning of any equations used to solve homographies, fundamental
  matrices etc.


  Inputs:
  pts: 3xN array of 2D homogeneous coordinates

  Returns:
  newpts: 3xN array of transformed 2D homogeneous coordinates.  The
          scaling parameter is normalised to 1 unless the point is at
          infinity.
  """
    if pts.shape[0] == 4:
        pts = hom_3d_to_2d(pts)

    if pts.shape[0] != 3 and pts.shape[0] != 4:
        print "Shape error"

    finiteind = np.nonzero(abs(pts[2, :]) > np.spacing(1))

    if len(finiteind[0]) != pts.shape[1]:
        print('Some points are at infinity')

    dist = []
    pts = pts / pts[2, :]
    for i in finiteind:
        c = np.mean(pts[0:2, i].T, axis=0).T
        newp1 = pts[0, i] - c[0]
        newp2 = pts[1, i] - c[1]
        dist.append(np.sqrt(newp1**2 + newp2**2))

    dist = np.array(dist)
    meandist = np.mean(dist)
    # scale = np.sqrt(2) / meandist # translate and scaling
    # scale = 1 # Only translate, no scaling
    scale = radius * np.sqrt(
        2
    ) / meandist  # translate and set the scale increasing with the radius(distance from cam to marker)
    T = np.array([[scale, 0, -scale * c[0]], [0, scale, -scale * c[1]],
                  [0, 0, 1]])
    newpts = np.dot(T, pts)
    return newpts, T
コード例 #19
0
def find_argmax(natparam_grad, num_nodes):
    """Given the gradient of tree_categorical_maximum w.r.t. the natural
  parameters, finds the argmax of the tree categorical's log-joint."""
    not_found = set(
        range(num_nodes))  # haven't found the argmax for these nodes
    argmax = [0 for _ in range(num_nodes)]
    factor_iter = chain(natparam_grad.single_onehot_xis.iteritems(),
                        natparam_grad.joint_onehot_xis.iteritems())

    while not_found:
        factor, param = factor_iter.next()
        if not_found.intersection(set(factor)):
            nonzero = np.nonzero(param)
            for i, node in enumerate(factor):
                argmax[node] = int(nonzero[i][0])
                not_found.discard(node)
    return argmax
コード例 #20
0
    def __init__(self, vec, other_vec, whole, otherwhole, actInd, **kwargs):
        actInd = (int(actInd[0]), int(actInd[1]))
        DistanceMat = np.array([[distance(i, j) for j in otherwhole]
                                for i in whole])

        # print("Mindistance:", np.min(DistanceMat))
        # print("len(whole),len(otherwhole)",len(whole),len(otherwhole))

        insectPT = np.nonzero(
            DistanceMat < INTERSECTLIM)  # The index of the intersection point
        try:
            insectPT = (insectPT[0][0], insectPT[1][0])
        except IndexError:  # the case where is no pair of points fall in the threshold, find the least distance point instead
            insectPT = np.unravel_index(np.argmin(DistanceMat, axis=None),
                                        DistanceMat.shape)

        egopath = whole[actInd[0]:insectPT[0]]
        otherpath = otherwhole[actInd[1]:insectPT[1]]
        # path a None in is just to call the lambda function
        egoPTs = np.sum(
            (self._distance(self._diff(lambda x: egopath[:, 0]),
                            self._diff(lambda y: egopath[:, 1])))(None))
        otherPTs = np.sum(
            self._distance(self._diff(lambda x: otherpath[:, 0]),
                           self._diff(lambda y: otherpath[:, 1]))(None))
        otherDistance = self._cumsum(
            self._distance(
                self._diff(lambda x: otherwhole[actInd[1]:, 0]),
                self._diff(lambda y: otherwhole[actInd[1]:, 1])))(None)
        self.other_vec = other_vec
        self.whole = whole
        self.otherwhole = otherwhole
        self.actInd = actInd
        self.insectPT = insectPT
        self.egoPTs = egoPTs
        self.otherPTs = otherPTs
        self.otherDistance = otherDistance
        super().__init__(vec,
                         other_vec,
                         whole=whole,
                         otherwhole=otherwhole,
                         actInd=actInd,
                         intersectInd=insectPT,
                         intersectPTs=(self.egoPTs, self.otherPTs),
                         otherDist=otherDistance,
                         **kwargs)
コード例 #21
0
def aff2rfnorm(aff):
    """Mirror plane normal vector and point from affine `aff`

    Parameters
    ----------
    aff : array-like, shape (4,4)

    Returns
    -------
    normal : array shape (3,)
       vector normal to point (and therefore mirror plane).
    point : array shape (3,)
       x, y, x coordinates of point that, together with normal, define the
       reflection plane.

    Raises
    ------
    ValueError
       If there is no eigenvector for ``aff[:3,:3]`` with eigenvalue -1
    ValueError
        If determinant of ``aff[:3, :3]`` is not close to -1
    ValueError
       If there is no eigenvector for `aff` with eigenvalue 1.

    Examples
    --------
    >>> v0 = np.random.random(3) - 0.5
    >>> v1 = np.random.random(3) - 0.5
    >>> M0 = rfnorm2aff(v0, v1)
    >>> normal, point = aff2rfnorm(M0)
    >>> M1 = rfnorm2aff(normal, point)
    >>> np.allclose(M0, M1)
    True
    """
    aff = np.asarray(aff)
    normal = mat2rfnorm(aff[:3, :3])
    # point: any unit eigenvector corresponding to eigenvalue 1
    l, V = np.linalg.eig(aff)
    near_1, = np.nonzero(abs(np.real(l.squeeze()) - 1.0) < 1e-8)
    if near_1.size == 0:
        raise ValueError("no eigenvector corresponding to eigenvalue 1")
    point = np.real(V[:, near_1[-1]]).squeeze()
    point = point[:3] / point[3]
    return normal, point
コード例 #22
0
def mat2rfnorm(mat):
    """Mirror plane normal vector from `mat` matrix.

    Parameters
    ----------
    mat : array-like, shape (3,3)

    Returns
    -------
    normal : array shape (3,)
       vector normal to point (and therefore mirror plane)

    Raises
    ------
    ValueError
       If there is no eigenvector with eigenvalue -1
    ValueError
       If determinant of `mat` is not close to -1

    Examples
    --------
    >>> normal = np.random.random(3) - 0.5
    >>> M0 = rfnorm2mat(normal)
    >>> normal = mat2rfnorm(M0)
    >>> M1 = rfnorm2mat(normal)
    >>> np.allclose(M0, M1)
    True
    """
    mat = np.asarray(mat)
    # normal: unit eigenvector corresponding to eigenvalue -1
    L, V = np.linalg.eig(mat)
    m1_factors, = np.nonzero(abs(np.real(L.squeeze()) + 1.0) < 1e-8)
    if m1_factors.size == 0:
        raise ValueError("no unit eigenvector corresponding to eigenvalue -1")
    if not np.abs(np.prod(L) + 1) < 1e-8:
        raise ValueError('Determinant should be -1')
    return np.real(V[:, m1_factors[0]]).squeeze()
コード例 #23
0
def alternateOptimization(opinion_matrix, opinion_matrix_I, rating_matrix,
                          NUM_OF_FACTORS, MAX_DEPTH, File):
    # Save and print the Number of Users and Movies
    NUM_USERS = rating_matrix.shape[0]
    NUM_MOVIES = rating_matrix.shape[1]
    NUM_FEATURE = opinion_matrix.shape[1]
    print("Number of Users", NUM_USERS)
    print("Number of Item", NUM_MOVIES)
    print("Number of Feature", NUM_FEATURE)
    print("Number of Latent Factors: ", NUM_OF_FACTORS)

    # Create the user and item profile vector of appropriate size.
    # Initialize the item vectors according to MF
    user_vectors, item_vectors = MF(20, 0.05, 0.02, 0.02, 50, File)
    #user_vectors = np.random.rand(NUM_USERS, NUM_OF_FACTORS)
    #item_vectors = np.random.rand(NUM_MOVIES, NUM_OF_FACTORS)

    i = 0
    print("Entering Main Loop of alternateOptimization")
    decTree = dtree.Tree(dtree.Node(None, 1), NUM_OF_FACTORS, MAX_DEPTH)
    # Do converge Check
    while i < 5:
        # Create the decision Tree based on item_vectors
        print("Creating Tree.. for i = ", i, "for user")
        decTree = dtree.Tree(dtree.Node(None, 1), NUM_OF_FACTORS, MAX_DEPTH)
        decTree.fitTree_U(decTree.root, opinion_matrix, rating_matrix,
                          item_vectors, NUM_OF_FACTORS)

        print("Getting the user vectors from tree")
        # Calculate the User vectors using dtree
        user_vectors_before = user_vectors
        user_vectors = decTree.getVectors_f(opinion_matrix, NUM_OF_FACTORS)
        # adding personalized term
        for index in range(len(rating_matrix)):
            indice = np.array([index])
            user_vectors[index] = opt.cf_user(rating_matrix, item_vectors,
                                              user_vectors[index], indice,
                                              NUM_OF_FACTORS)

        print("Creating Tree.. for i = ", i, "for item")
        decTreeI = dtree.Tree(dtree.Node(None, 1), NUM_OF_FACTORS, MAX_DEPTH)
        decTreeI.fitTree_I(decTreeI.root, opinion_matrix_I, rating_matrix,
                           user_vectors, NUM_OF_FACTORS)

        print("Getting the item vectors from tree")
        item_vectors_before = item_vectors
        item_vectors = decTreeI.getVectors_f(opinion_matrix_I, NUM_OF_FACTORS)
        for index in range(len(rating_matrix[0])):
            indice = np.array([index])
            item_vectors[index] = opt.cf_item(rating_matrix, user_vectors,
                                              item_vectors[index], indice,
                                              NUM_OF_FACTORS)

        # Calculate Error for Convergence check
        Pred_before = np.dot(user_vectors_before, item_vectors_before.T)
        Pred = np.dot(user_vectors, item_vectors.T)
        Error = Pred_before - Pred
        Error = Error[np.nonzero(Error)]
        error = np.dot(Error, Error)
        if error < 0.1:
            break
        i = i + 1

    return decTree, decTreeI, user_vectors, item_vectors
コード例 #24
0
        save_images(sample[0, :, :], 'a3plotsample.png')

        ## uncomment for Question 2f)
        # plot_posterior_contours(mean_params,logstd_params)

        print(iter)
        print(objective(var_params,iter))

# The optimizers provided by autograd can optimize lists, tuples, or dicts of parameters.
# You may use these optimizers for Q4, but implement your own gradient descent optimizer for Q3!
optimized_params = adam(objective_grad, init_params, step_size=0.05, num_iters=60, callback=print_perf)


#predictions for test
predict_test = predict_regression(test_images, np.transpose(optimized_params[0])) #A3 q1/A2 code 
total_correct_test = np.sum(np.nonzero(predict_test)[1] == np.nonzero(test_labels)[1]) #get total number of correct predictions
accuracy_test = total_correct_test/float(test_labels.shape[0])    #get accuracy    
print('\nTest Accuracy ',accuracy_test)

##testing a bunch of std values, std = 1 is best with 77.68% and std =9 is second best 77.09%
#for i in range(1,10):
    #prior_std = i**2  # from 5 to 100
    #print(prior_std)
    #optimized_params = adam(objective_grad, init_params, step_size=0.05, num_iters=100, callback=print_perf) 
    #predict_test = predict_regression(test_images, np.transpose(optimized_params[0])) #A3 q1/A2 code 
    #total_correct_test = np.sum(np.nonzero(predict_test)[1] == np.nonzero(test_labels)[1]) #get total number of correct predictions
    #accuracy_test = total_correct_test/float(test_labels.shape[0])    #get accuracy    
    #print('\nTest Accuracy ',accuracy_test)    
    
    #prior_std = 1/i**2   #from 1 to 1/100
    #print(prior_std)
コード例 #25
0
def reconstruct_ptychography(
        # ______________________________________
        # |Raw data and experimental parameters|________________________________
        fname, probe_pos, probe_size, obj_size, theta_st=0, theta_end=PI, n_theta=None, theta_downsample=None,
        energy_ev=5000, psize_cm=1e-7, free_prop_cm=None,
        # ___________________________
        # |Reconstruction parameters|___________________________________________
        n_epochs='auto', crit_conv_rate=0.03, max_nepochs=200, alpha_d=None, alpha_b=None,
        gamma=1e-6, learning_rate=1.0, minibatch_size=None, multiscale_level=1, n_epoch_final_pass=None,
        initial_guess=None, n_batch_per_update=1, reweighted_l1=False, interpolation='bilinear',
        # ___________________________
        # |Finite support constraint|___________________________________________
        finite_support_mask_path=None, shrink_cycle=None, shrink_threshold=1e-9,
        # ___________________
        # |Object contraints|
        object_type='normal',
        # _______________
        # |Forward model|_______________________________________________________
        forward_algorithm='fresnel', binning=1, fresnel_approx=False, pure_projection=False, two_d_mode=False,
        probe_type='gaussian', probe_initial=None,
        # _____
        # |I/O|_________________________________________________________________
        save_path='.', output_folder=None, save_intermediate=False, full_intermediate=False, use_checkpoint=True,
        save_stdout=False,
        # _____________
        # |Performance|_________________________________________________________
        cpu_only=False, core_parallelization=True, shared_file_object=True, n_dp_batch=20,
        # __________________________
        # |Object optimizer options|____________________________________________
        optimizer='adam',
        # _________________________
        # |Other optimizer options|_____________________________________________
        probe_learning_rate=1e-3,
        optimize_probe_defocusing=False, probe_defocusing_learning_rate=1e-5,
        optimize_probe_pos_offset=False,
        # ________________
        # |Other settings|______________________________________________________
        dynamic_rate=True, pupil_function=None, probe_circ_mask=0.9, dynamic_dropping=False, dropping_threshold=8e-5,
        **kwargs,):
        # ______________________________________________________________________

    """
    Notes:
        1. Input data are assumed to be contained in an HDF5 under 'exchange/data', as a 4D dataset of
           shape [n_theta, n_spots, detector_size_y, detector_size_x].
        2. Full-field reconstruction is treated as ptychography. If the image is not divided, the programs
           runs as if it is dealing with ptychography with only 1 spot per angle.
        3. Full-field reconstruction with minibatch_size > 1 but without image dividing is not supported.
           In this case, minibatch_size will be forced to be 1, so that each rank process only one
           rotation angle's image at a time. To perform large fullfield reconstruction efficiently,
           divide the data into sub-chunks.
        4. Full-field reconstruction using shared_file_mode but without image dividing is not recommended
           even if minibatch_size is 1. In shared_file_mode, all ranks process data from the same rotation
           angle in each synchronized batch. Doing this will cause all ranks to process the same data.
           To perform large fullfield reconstruction efficiently, divide the data into sub-chunks.
    """

    def calculate_loss(obj_delta, obj_beta, probe_real, probe_imag, probe_defocus_mm, probe_pos_offset, this_i_theta, this_pos_batch, this_prj_batch):

        if optimize_probe_defocusing:
            h_probe = get_kernel(probe_defocus_mm * 1e6, lmbda_nm, voxel_nm, probe_size, fresnel_approx=fresnel_approx)
            probe_complex = probe_real + 1j * probe_imag
            probe_complex = np.fft.ifft2(np.fft.ifftshift(np.fft.fftshift(np.fft.fft2(probe_complex)) * h_probe))
            probe_real = np.real(probe_complex)
            probe_imag = np.imag(probe_complex)

        if optimize_probe_pos_offset:
            this_pos_batch = this_pos_batch + probe_pos_offset[this_i_theta]
        if not shared_file_object:
            obj_stack = np.stack([obj_delta, obj_beta], axis=3)
            if not two_d_mode:
                obj_rot = apply_rotation(obj_stack, coord_ls[this_i_theta])
                # obj_rot = sp_rotate(obj_stack, theta, axes=(1, 2), reshape=False)
            else:
                obj_rot = obj_stack
            probe_pos_batch_ls = []
            exiting_ls = []
            i_dp = 0
            while i_dp < minibatch_size:
                probe_pos_batch_ls.append(this_pos_batch[i_dp:min([i_dp + n_dp_batch, minibatch_size])])
                i_dp += n_dp_batch

            # Pad if needed
            obj_rot, pad_arr = pad_object(obj_rot, this_obj_size, probe_pos, probe_size)

            for k, pos_batch in enumerate(probe_pos_batch_ls):
                subobj_ls = []
                for j in range(len(pos_batch)):
                    pos = pos_batch[j]
                    pos = [int(x) for x in pos]
                    pos[0] = pos[0] + pad_arr[0, 0]
                    pos[1] = pos[1] + pad_arr[1, 0]
                    subobj = obj_rot[pos[0]:pos[0] + probe_size[0], pos[1]:pos[1] + probe_size[1], :, :]
                    subobj_ls.append(subobj)

                subobj_ls = np.stack(subobj_ls)
                exiting = multislice_propagate_batch_numpy(subobj_ls[:, :, :, :, 0], subobj_ls[:, :, :, :, 1], probe_real,
                                                           probe_imag, energy_ev, psize_cm * ds_level, kernel=h, free_prop_cm=free_prop_cm,
                                                           obj_batch_shape=[len(pos_batch), *probe_size, this_obj_size[-1]],
                                                           fresnel_approx=fresnel_approx, pure_projection=pure_projection)
                exiting_ls.append(exiting)
            exiting_ls = np.concatenate(exiting_ls, 0)
            loss = np.mean((np.abs(exiting_ls) - np.abs(this_prj_batch)) ** 2)

        else:
            probe_pos_batch_ls = []
            exiting_ls = []
            i_dp = 0
            while i_dp < minibatch_size:
                probe_pos_batch_ls.append(this_pos_batch[i_dp:min([i_dp + n_dp_batch, minibatch_size])])
                i_dp += n_dp_batch

            pos_ind = 0
            for k, pos_batch in enumerate(probe_pos_batch_ls):
                subobj_ls_delta = obj_delta[pos_ind:pos_ind + len(pos_batch), :, :, :]
                subobj_ls_beta = obj_beta[pos_ind:pos_ind + len(pos_batch), :, :, :]
                exiting = multislice_propagate_batch_numpy(subobj_ls_delta, subobj_ls_beta, probe_real,
                                                           probe_imag, energy_ev, psize_cm * ds_level, kernel=h,
                                                           free_prop_cm=free_prop_cm,
                                                           obj_batch_shape=[len(pos_batch), *probe_size,
                                                                            this_obj_size[-1]],
                                                           fresnel_approx=fresnel_approx,
                                                           pure_projection=pure_projection)
                exiting_ls.append(exiting)
                pos_ind += len(pos_batch)
            exiting_ls = np.concatenate(exiting_ls, 0)
            loss = np.mean((np.abs(exiting_ls) - np.abs(this_prj_batch)) ** 2)
            # dxchange.write_tiff(abs(exiting_ls._value[0]), output_folder + '/det/det', dtype='float32', overwrite=True)
            # raise

        # Regularization
        if reweighted_l1:
            if alpha_d not in [None, 0]:
                loss = loss + alpha_d * np.mean(weight_l1 * np.abs(obj_delta))
            if alpha_b not in [None, 0]:
                loss = loss + alpha_b * np.mean(weight_l1 * np.abs(obj_beta))
        else:
            if alpha_d not in [None, 0]:
                loss = loss + alpha_d * np.mean(np.abs(obj_delta))
            if alpha_b not in [None, 0]:
                loss = loss + alpha_b * np.mean(np.abs(obj_beta))
        if gamma not in [None, 0]:
            if shared_file_object:
                loss = loss + gamma * total_variation_3d(obj_delta, axis_offset=1)
            else:
                loss = loss + gamma * total_variation_3d(obj_delta, axis_offset=0)

        # Write convergence data
        global current_loss
        current_loss = loss._value
        f_conv.write('{},{},{},'.format(i_epoch, i_batch, current_loss))
        f_conv.flush()

        return loss

    comm = MPI.COMM_WORLD
    n_ranks = comm.Get_size()
    rank = comm.Get_rank()
    t_zero = time.time()

    timestr = str(datetime.datetime.today())
    timestr = timestr[:timestr.find('.')]
    for i in [':', '-', ' ']:
        if i == ' ':
            timestr = timestr.replace(i, '_')
        else:
            timestr = timestr.replace(i, '')

    # ================================================================================
    # Create pointer for raw data.
    # ================================================================================
    t0 = time.time()
    print_flush('Reading data...', 0, rank)
    f = h5py.File(os.path.join(save_path, fname), 'r')
    prj = f['exchange/data']
    if n_theta is None:
        n_theta = prj.shape[0]
    if two_d_mode:
        n_theta = 1
    prj_theta_ind = np.arange(n_theta, dtype=int)
    theta = -np.linspace(theta_st, theta_end, n_theta, dtype='float32')
    if theta_downsample is not None:
        theta = theta[::theta_downsample]
        prj_theta_ind = prj_theta_ind[::theta_downsample]
        n_theta = len(theta)
    original_shape = [n_theta, *prj.shape[1:]]

    print_flush('Data reading: {} s'.format(time.time() - t0), 0, rank)
    print_flush('Data shape: {}'.format(original_shape), 0, rank)
    comm.Barrier()

    not_first_level = False
    stdout_options = {'save_stdout': save_stdout, 'output_folder': output_folder, 
                      'timestamp': timestr}

    n_pos = len(probe_pos)
    probe_pos = np.array(probe_pos)

    # ================================================================================
    # Batching check.
    # ================================================================================
    if minibatch_size > 1 and n_pos == 1:
        warnings.warn('It seems that you are processing undivided fullfield data with'
                      'minibatch > 1. A rank can only process data from the same rotation'
                      'angle at a time. I am setting minibatch_size to 1.')
        minibatch_size = 1
    if shared_file_object and n_pos == 1:
        warnings.warn('It seems that you are processing undivided fullfield data with'
                      'shared_file_object=True. In shared-file mode, all ranks must'
                      'process data from the same rotation angle in each synchronized'
                      'batch.')

    # ================================================================================
    # Set output folder name if not specified.
    # ================================================================================
    if output_folder is None:
        output_folder = 'recon_{}'.format(timestr)
        if abs(PI - theta_end) < 1e-3:
            output_folder += '_180'
    print_flush('Output folder is {}'.format(output_folder), 0, rank)

    if save_path != '.':
        output_folder = os.path.join(save_path, output_folder)

    for ds_level in range(multiscale_level - 1, -1, -1):

        # ================================================================================
        # Set metadata.
        # ================================================================================
        ds_level = 2 ** ds_level
        print_flush('Multiscale downsampling level: {}'.format(ds_level), 0, rank, **stdout_options)
        comm.Barrier()

        prj_shape = original_shape

        if ds_level > 1:
            this_obj_size = [int(x / ds_level) for x in obj_size]
        else:
            this_obj_size = obj_size

        dim_y, dim_x = prj_shape[-2:]
        if minibatch_size is None:
            minibatch_size = n_pos
        comm.Barrier()

        # ================================================================================
        # Create output directory.
        # ================================================================================
        if rank == 0:
            try:
                os.makedirs(os.path.join(output_folder))
            except:
                print('Target folder {} exists.'.format(output_folder))
        comm.Barrier()

        # ================================================================================
        # Create object function optimizer.
        # ================================================================================
        if optimizer == 'adam':
            opt = AdamOptimizer([*this_obj_size, 2], output_folder=output_folder)
            optimizer_options_obj = {'step_size': learning_rate,
                                     'shared_file_object': shared_file_object}
        elif optimizer == 'gd':
            opt = GDOptimizer([*this_obj_size, 2], output_folder=output_folder)
            optimizer_options_obj = {'step_size': learning_rate,
                                     'dynamic_rate': True,
                                     'first_downrate_iteration': 20 * max([ceil(n_pos / (minibatch_size * n_ranks)), 1])}
        if shared_file_object:
            opt.create_file_objects(use_checkpoint=use_checkpoint)
        else:
            if use_checkpoint:
                try:
                    opt.restore_param_arrays_from_checkpoint()
                except:
                    opt.create_param_arrays()
            else:
                opt.create_param_arrays()

        # ================================================================================
        # Read rotation data.
        # ================================================================================
        try:
            coord_ls = read_all_origin_coords('arrsize_{}_{}_{}_ntheta_{}'.format(*this_obj_size, n_theta),
                                              n_theta)
        except:
            if rank == 0:
                print_flush('Saving rotation coordinates...', 0, rank, **stdout_options)
                save_rotation_lookup(this_obj_size, n_theta)
            comm.Barrier()
            coord_ls = read_all_origin_coords('arrsize_{}_{}_{}_ntheta_{}'.format(*this_obj_size, n_theta),
                                              n_theta)

        # ================================================================================
        # Unify random seed for all threads.
        # ================================================================================
        comm.Barrier()
        seed = int(time.time() / 60)
        np.random.seed(seed)
        comm.Barrier()

        # ================================================================================
        # Get checkpointed parameters.
        # ================================================================================
        starting_epoch, starting_batch = (0, 0)
        needs_initialize = False if use_checkpoint else True
        if use_checkpoint and shared_file_object:
            try:
                starting_epoch, starting_batch = restore_checkpoint(output_folder, shared_file_object)
            except:
                needs_initialize = True

        elif use_checkpoint and (not shared_file_object):
            try:
                starting_epoch, starting_batch, obj_delta, obj_beta = restore_checkpoint(output_folder, shared_file_object, opt)
            except:
                needs_initialize = True

        # ================================================================================
        # Create object class.
        # ================================================================================
        obj = ObjectFunction([*this_obj_size, 2], shared_file_object=shared_file_object,
                             output_folder=output_folder, ds_level=ds_level, object_type=object_type)
        if shared_file_object:
            obj.create_file_object(use_checkpoint)
            obj.create_temporary_file_object()
            if needs_initialize:
                obj.initialize_file_object(save_stdout=save_stdout, timestr=timestr,
                                           not_first_level=not_first_level, initial_guess=initial_guess)
        else:
            if needs_initialize:
                obj.initialize_array(save_stdout=save_stdout, timestr=timestr,
                                     not_first_level=not_first_level, initial_guess=initial_guess)
            else:
                obj.delta = obj_delta
                obj.beta = obj_beta

        # ================================================================================
        # Create gradient class.
        # ================================================================================
        gradient = Gradient(obj)
        if shared_file_object:
            gradient.create_file_object()
            gradient.initialize_gradient_file()
        else:
            gradient.initialize_array_with_values(np.zeros(this_obj_size), np.zeros(this_obj_size))

        # ================================================================================
        # If a finite support mask path is specified (common for full-field imaging),
        # create an instance of monochannel mask class. While finite_support_mask_path
        # has to point to a 3D tiff file, the mask will be written as an HDF5 if
        # share_file_mode is True.
        # ================================================================================
        mask = None
        if finite_support_mask_path is not None:
            mask = Mask(this_obj_size, finite_support_mask_path, shared_file_object=shared_file_object,
                        output_folder=output_folder, ds_level=ds_level)
            if shared_file_object:
                mask.create_file_object(use_checkpoint=use_checkpoint)
                mask.initialize_file_object()
            else:
                mask_arr = dxchange.read_tiff(finite_support_mask_path)
                mask.initialize_array_with_values(mask_arr)

        # ================================================================================
        # Initialize probe functions.
        # ================================================================================
        print_flush('Initialzing probe...', 0, rank, **stdout_options)
        probe_real, probe_imag = initialize_probe(probe_size, probe_type, pupil_function=pupil_function, probe_initial=probe_initial,
                             save_stdout=save_stdout, output_folder=output_folder, timestr=timestr,
                             save_path=save_path, fname=fname, **kwargs)

        # ================================================================================
        # generate Fresnel kernel.
        # ================================================================================
        voxel_nm = np.array([psize_cm] * 3) * 1.e7 * ds_level
        lmbda_nm = 1240. / energy_ev
        delta_nm = voxel_nm[-1]
        h = get_kernel(delta_nm * binning, lmbda_nm, voxel_nm, probe_size, fresnel_approx=fresnel_approx)

        # ================================================================================
        # Create other optimizers (probe, probe defocus, probe positions, etc.).
        # ================================================================================
        opt_arg_ls = [0, 1]
        if probe_type == 'optimizable':
            opt_probe = GDOptimizer([*probe_size, 2], output_folder=output_folder)
            optimizer_options_probe = {'step_size': probe_learning_rate,
                                      'dynamic_rate': True,
                                      'first_downrate_iteration': 4 * max([ceil(n_pos / (minibatch_size * n_ranks)), 1])}
            opt_arg_ls = opt_arg_ls + [2, 3]
            opt_probe.set_index_in_grad_return(len(opt_arg_ls))

        probe_defocus_mm = np.array(0.0)
        if optimize_probe_defocusing:
            opt_probe_defocus = GDOptimizer([1], output_folder=output_folder)
            optimizer_options_probe_defocus = {'step_size': probe_defocusing_learning_rate,
                                               'dynamic_rate': True,
                                               'first_downrate_iteration': 4 * max([ceil(n_pos / (minibatch_size * n_ranks)), 1])}
            opt_arg_ls.append(4)
            opt_probe_defocus.set_index_in_grad_return(len(opt_arg_ls))

        probe_pos_offset = np.zeros([n_theta, 2])
        if optimize_probe_pos_offset:
            opt_probe_pos_offset = GDOptimizer(probe_pos_offset.shape, output_folder=output_folder)
            optimizer_options_probe_pos_offset = {'step_size': 0.5,
                                                  'dynamic_rate': False}
            opt_arg_ls.append(5)
            opt_probe_pos_offset.set_index_in_grad_return(len(opt_arg_ls))

        # ================================================================================
        # Get gradient of loss function w.r.t. optimizable variables.
        # ================================================================================
        loss_grad = grad(calculate_loss, opt_arg_ls)

        # ================================================================================
        # Save convergence data.
        # ================================================================================
        if rank == 0:
            try:
                os.makedirs(os.path.join(output_folder, 'convergence'))
            except:
                pass
        comm.Barrier()
        f_conv = open(os.path.join(output_folder, 'convergence', 'loss_rank_{}.txt'.format(rank)), 'w')
        f_conv.write('i_epoch,i_batch,loss,time\n')

        # ================================================================================
        # Create parameter summary file.
        # ================================================================================
        print_flush('Optimizer started.', 0, rank, **stdout_options)
        if rank == 0:
            create_summary(output_folder, locals(), preset='ptycho')

        # ================================================================================
        # Start outer (epoch) loop.
        # ================================================================================
        cont = True
        i_epoch = starting_epoch
        m_p, v_p, m_pd, v_pd = (None, None, None, None)
        while cont:
            n_pos = len(probe_pos)
            n_spots = n_theta * n_pos
            n_tot_per_batch = minibatch_size * n_ranks
            n_batch = int(np.ceil(float(n_spots) / n_tot_per_batch))

            t0 = time.time()
            spots_ls = range(n_spots)
            ind_list_rand = []

            t00 = time.time()
            print_flush('Allocating jobs over threads...', 0, rank, **stdout_options)
            # Make a list of all thetas and spot positions'
            np.random.seed(i_epoch)
            comm.Barrier()
            if not two_d_mode:
                theta_ls = np.arange(n_theta)
                np.random.shuffle(theta_ls)
            else:
                theta_ls = np.linspace(0, 2 * PI, prj.shape[0])
                theta_ls = abs(theta_ls - theta_st) < 1e-5
                i_theta = np.nonzero(theta_ls)[0][0]
                theta_ls = np.array([i_theta])

            # ================================================================================
            # Put diffraction spots from all angles together, and divide into minibatches.
            # ================================================================================
            for i, i_theta in enumerate(theta_ls):
                spots_ls = range(n_pos)
                # ================================================================================
                # Append randomly selected diffraction spots if necessary, so that a rank won't be given
                # spots from different angles in one batch.
                # When using shared file object, we must also ensure that all ranks deal with data at the
                # same angle at a time.
                # ================================================================================
                if not shared_file_object and n_pos % minibatch_size != 0:
                    spots_ls = np.append(spots_ls, np.random.choice(spots_ls,
                                                                    minibatch_size - (n_pos % minibatch_size),
                                                                    replace=False))
                elif shared_file_object and n_pos % n_tot_per_batch != 0:
                    spots_ls = np.append(spots_ls, np.random.choice(spots_ls,
                                                                    n_tot_per_batch - (n_pos % n_tot_per_batch),
                                                                    replace=False))
                # ================================================================================
                # Create task list for the current angle.
                # ind_list_rand is in the format of [((5, 0), (5, 1), ...), ((17, 0), (17, 1), ..., (...))]
                #                                    |___________________|   |_____|
                #                       a batch for all ranks  _|               |_ (i_theta, i_spot)
                #                    (minibatch_size * n_ranks)
                # ================================================================================
                if i == 0:
                    ind_list_rand = np.vstack([np.array([i_theta] * len(spots_ls)), spots_ls]).transpose()
                else:
                    ind_list_rand = np.concatenate(
                        [ind_list_rand, np.vstack([np.array([i_theta] * len(spots_ls)), spots_ls]).transpose()], axis=0)
            ind_list_rand = split_tasks(ind_list_rand, n_tot_per_batch)

            print_flush('Allocation done in {} s.'.format(time.time() - t00), 0, rank, **stdout_options)

            current_i_theta = 0
            for i_batch in range(starting_batch, n_batch):

                # ================================================================================
                # Initialize.
                # ================================================================================
                print_flush('Epoch {}, batch {} of {} started.'.format(i_epoch, i_batch, n_batch), 0, rank, **stdout_options)
                opt.i_batch = 0

                # ================================================================================
                # Save checkpoint.
                # ================================================================================
                if shared_file_object:
                    save_checkpoint(i_epoch, i_batch, output_folder, shared_file_object=True,
                                    obj_array=None, optimizer=opt)
                    obj.f.flush()
                else:
                    save_checkpoint(i_epoch, i_batch, output_folder, shared_file_object=False,
                                    obj_array=np.stack([obj.delta, obj.beta], axis=-1), optimizer=opt)

                # ================================================================================
                # Get scan position, rotation angle indices, and raw data for current batch.
                # ================================================================================
                t00 = time.time()
                if len(ind_list_rand[i_batch]) < n_tot_per_batch:
                    n_supp = n_tot_per_batch - len(ind_list_rand[i_batch])
                    ind_list_rand[i_batch] = np.concatenate([ind_list_rand[i_batch], ind_list_rand[0][:n_supp]])

                this_ind_batch = ind_list_rand[i_batch]
                this_i_theta = this_ind_batch[rank * minibatch_size, 0]
                this_ind_rank = np.sort(this_ind_batch[rank * minibatch_size:(rank + 1) * minibatch_size, 1])
                this_pos_batch = probe_pos[this_ind_rank]
                print_flush('Current rank is processing angle ID {}.'.format(this_i_theta), 0, rank, **stdout_options)

                t_prj_0 = time.time()
                this_prj_batch = prj[this_i_theta, this_ind_rank]
                print_flush('  Raw data reading done in {} s.'.format(time.time() - t_prj_0), 0, rank, **stdout_options)

                # ================================================================================
                # In shared file mode, if moving to a new angle, rotate the HDF5 object and saved
                # the rotated object into the temporary file object.
                # ================================================================================
                if shared_file_object and this_i_theta != current_i_theta:
                    current_i_theta = this_i_theta
                    print_flush('  Rotating dataset...', 0, rank, **stdout_options)
                    t_rot_0 = time.time()
                    obj.rotate_data_in_file(coord_ls[this_i_theta], interpolation=interpolation, dset_2=obj.dset_rot)
                    # opt.rotate_files(coord_ls[this_i_theta], interpolation=interpolation)
                    # if mask is not None: mask.rotate_data_in_file(coord_ls[this_i_theta], interpolation=interpolation)
                    comm.Barrier()
                    print_flush('  Dataset rotation done in {} s.'.format(time.time() - t_rot_0), 0, rank, **stdout_options)

                if ds_level > 1:
                    this_prj_batch = this_prj_batch[:, :, ::ds_level, ::ds_level]
                comm.Barrier()

                if shared_file_object:
                    # ================================================================================
                    # Get values for local chunks of object_delta and beta; interpolate and read directly from HDF5
                    # ================================================================================
                    t_read_0 = time.time()
                    obj_rot = obj.read_chunks_from_file(this_pos_batch, probe_size, dset_2=obj.dset_rot)
                    print_flush('  Chunk reading done in {} s.'.format(time.time() - t_read_0), 0, rank, **stdout_options)
                    obj_delta = np.array(obj_rot[:, :, :, :, 0])
                    obj_beta = np.array(obj_rot[:, :, :, :, 1])
                    opt.get_params_from_file(this_pos_batch, probe_size)
                else:
                    obj_delta = obj.delta
                    obj_beta = obj.beta

                # Update weight for reweighted L1
                if shared_file_object:
                    weight_l1 = np.max(obj_delta) / (abs(obj_delta) + 1e-8)
                else:
                    if i_batch % 10 == 0: weight_l1 = np.max(obj_delta) / (abs(obj_delta) + 1e-8)

                # ================================================================================
                # Calculate object gradients.
                # ================================================================================
                t_grad_0 = time.time()
                grads = loss_grad(obj_delta, obj_beta, probe_real, probe_imag, probe_defocus_mm, probe_pos_offset, this_i_theta, this_pos_batch, this_prj_batch)
                print_flush('  Gradient calculation done in {} s.'.format(time.time() - t_grad_0), 0, rank, **stdout_options)
                grads = list(grads)

                # ================================================================================
                # Reshape object gradient to [y, x, z, c] or [n, y, x, z, c] and average over
                # ranks.
                # ================================================================================
                if shared_file_object:
                    obj_grads = np.stack(grads[:2], axis=-1)
                else:
                    this_obj_grads = np.stack(grads[:2], axis=-1)
                    obj_grads = np.zeros_like(this_obj_grads)
                    comm.Barrier()
                    comm.Allreduce(this_obj_grads, obj_grads)
                obj_grads = obj_grads / n_ranks

                # ================================================================================
                # Update object function with optimizer if not shared_file_object; otherwise,
                # just save the gradient chunk into the gradient file.
                # ================================================================================
                if not shared_file_object:
                    effective_iter = i_batch // max([ceil(n_pos / (minibatch_size * n_ranks)), 1])
                    obj_temp = opt.apply_gradient(np.stack([obj_delta, obj_beta], axis=-1), obj_grads, effective_iter,
                                                            **optimizer_options_obj)
                    obj_delta = np.take(obj_temp, 0, axis=-1)
                    obj_beta = np.take(obj_temp, 1, axis=-1)
                else:
                    t_grad_write_0 = time.time()
                    gradient.write_chunks_to_file(this_pos_batch, np.take(obj_grads, 0, axis=-1),
                                                  np.take(obj_grads, 1, axis=-1), probe_size,
                                                  write_difference=False)
                    print_flush('  Gradient writing done in {} s.'.format(time.time() - t_grad_write_0), 0, rank, **stdout_options)
                # ================================================================================
                # Nonnegativity and phase/absorption-only constraints for non-shared-file-mode,
                # and update arrays in instance.
                # ================================================================================
                if not shared_file_object:
                    obj_delta = np.clip(obj_delta, 0, None)
                    obj_beta = np.clip(obj_beta, 0, None)
                    if object_type == 'absorption_only': obj_delta[...] = 0
                    if object_type == 'phase_only': obj_beta[...] = 0
                    obj.delta = obj_delta
                    obj.beta = obj_beta

                # ================================================================================
                # Optimize probe and other parameters if necessary.
                # ================================================================================
                if probe_type == 'optimizable':
                    this_probe_grads = np.stack(grads[2:4], axis=-1)
                    probe_grads = np.zeros_like(this_probe_grads)
                    comm.Allreduce(this_probe_grads, probe_grads)
                    probe_grads = probe_grads / n_ranks
                    probe_temp = opt_probe.apply_gradient(np.stack([probe_real, probe_imag], axis=-1), probe_grads, **optimizer_options_probe)
                    probe_real = np.take(probe_temp, 0, axis=-1)
                    probe_imag = np.take(probe_temp, 1, axis=-1)

                if optimize_probe_defocusing:
                    this_pd_grad = np.array(grads[opt_probe_defocus.index_in_grad_returns])
                    pd_grads = np.array(0.0)
                    comm.Allreduce(this_pd_grad, pd_grads)
                    pd_grads = pd_grads / n_ranks
                    probe_defocus_mm = opt_probe_defocus.apply_gradient(probe_defocus_mm, pd_grads,
                                                                        **optimizer_options_probe_defocus)
                    print_flush('  Probe defocus is {} mm.'.format(probe_defocus_mm), 0, rank,
                                **stdout_options)

                if optimize_probe_pos_offset:
                    this_pos_offset_grad = np.array(grads[optimize_probe_pos_offset.index_in_grad_returns])
                    pos_offset_grads = np.zeros_like(probe_pos_offset)
                    comm.Allreduce(this_pos_offset_grad, pos_offset_grads)
                    pos_offset_grads = pos_offset_grads / n_ranks
                    probe_pos_offset = opt_probe_pos_offset.apply_gradient(probe_pos_offset, pos_offset_grads,
                                                                        **optimizer_options_probe_pos_offset)

                # ================================================================================
                # For shared-file-mode, if finishing or above to move to a different angle,
                # rotate the gradient back, and use it to update the object at 0 deg. Then
                # update the object using gradient at 0 deg.
                # ================================================================================
                if shared_file_object and (i_batch == n_batch - 1 or ind_list_rand[i_batch + 1][0, 0] != current_i_theta):
                    coord_new = read_origin_coords('arrsize_{}_{}_{}_ntheta_{}'.format(*this_obj_size, n_theta),
                                                   this_i_theta, reverse=True)
                    print_flush('  Rotating gradient dataset back...', 0, rank, **stdout_options)
                    t_rot_0 = time.time()
                    # dxchange.write_tiff(gradient.dset[:, :, :, 0], 'adhesin/test_shared_file/grad_prerot', dtype='float32')
                    # gradient.reverse_rotate_data_in_file(coord_ls[this_i_theta], interpolation=interpolation)
                    gradient.rotate_data_in_file(coord_new, interpolation=interpolation)
                    # dxchange.write_tiff(gradient.dset[:, :, :, 0], 'adhesin/test_shared_file/grad_postrot', dtype='float32')
                    # comm.Barrier()
                    print_flush('  Gradient rotation done in {} s.'.format(time.time() - t_rot_0), 0, rank, **stdout_options)

                    t_apply_grad_0 = time.time()
                    opt.apply_gradient_to_file(obj, gradient, **optimizer_options_obj)
                    print_flush('  Object update done in {} s.'.format(time.time() - t_apply_grad_0), 0, rank, **stdout_options)
                    gradient.initialize_gradient_file()

                # ================================================================================
                # Apply finite support mask if specified.
                # ================================================================================
                if mask is not None:
                    if not shared_file_object:
                        obj.apply_finite_support_mask_to_array(mask)
                    else:
                        obj.apply_finite_support_mask_to_file(mask)
                    print_flush('  Mask applied.', 0, rank, **stdout_options)

                # ================================================================================
                # Update finite support mask if necessary.
                # ================================================================================
                if mask is not None and shrink_cycle is not None:
                    if i_batch % shrink_cycle == 0 and i_batch > 0:
                        if shared_file_object:
                            mask.update_mask_file(obj, shrink_threshold)
                        else:
                            mask.update_mask_array(obj, shrink_threshold)
                        print_flush('  Mask updated.', 0, rank, **stdout_options)

                # ================================================================================
                # Save intermediate object.
                # ================================================================================
                if rank == 0 and save_intermediate:
                    if shared_file_object:
                        dxchange.write_tiff(obj.dset[:, :, :, 0],
                                            fname=os.path.join(output_folder, 'intermediate', 'current'.format(ds_level)),
                                            dtype='float32', overwrite=True)
                    else:
                        dxchange.write_tiff(obj.delta,
                                            fname=os.path.join(output_folder, 'intermediate', 'current'.format(ds_level)),
                                            dtype='float32', overwrite=True)
                comm.Barrier()
                print_flush('Minibatch done in {} s; loss (rank 0) is {}.'.format(time.time() - t00, current_loss), 0, rank, **stdout_options)
                f_conv.write('{}\n'.format(time.time() - t_zero))
                f_conv.flush()

            if n_epochs == 'auto':
                    pass
            else:
                if i_epoch == n_epochs - 1: cont = False

            i_epoch = i_epoch + 1

            average_loss = 0
            print_flush(
                'Epoch {} (rank {}); Delta-t = {} s; current time = {} s,'.format(i_epoch, rank,
                                                                    time.time() - t0, time.time() - t_zero), **stdout_options)
            if rank == 0 and save_intermediate:
                if shared_file_object:
                    dxchange.write_tiff(obj.dset[:, :, :, 0],
                                        fname=os.path.join(output_folder, 'delta_ds_{}'.format(ds_level)),
                                        dtype='float32', overwrite=True)
                    dxchange.write_tiff(obj.dset[:, :, :, 1],
                                        fname=os.path.join(output_folder, 'beta_ds_{}'.format(ds_level)),
                                        dtype='float32', overwrite=True)
                    dxchange.write_tiff(np.sqrt(probe_real ** 2 + probe_imag ** 2),
                                        fname=os.path.join(output_folder, 'probe_mag_ds_{}'.format(ds_level)),
                                        dtype='float32', overwrite=True)
                    dxchange.write_tiff(np.arctan2(probe_imag, probe_real),
                                        fname=os.path.join(output_folder, 'probe_phase_ds_{}'.format(ds_level)),
                                        dtype='float32', overwrite=True)
                else:
                    dxchange.write_tiff(obj.delta,
                                        fname=os.path.join(output_folder, 'delta_ds_{}'.format(ds_level)),
                                        dtype='float32', overwrite=True)
                    dxchange.write_tiff(obj.beta,
                                        fname=os.path.join(output_folder, 'beta_ds_{}'.format(ds_level)),
                                        dtype='float32', overwrite=True)
                    dxchange.write_tiff(np.sqrt(probe_real ** 2 + probe_imag ** 2),
                                        fname=os.path.join(output_folder, 'probe_mag_ds_{}'.format(ds_level)),
                                        dtype='float32', overwrite=True)
                    dxchange.write_tiff(np.arctan2(probe_imag, probe_real),
                                        fname=os.path.join(output_folder, 'probe_phase_ds_{}'.format(ds_level)),
                                        dtype='float32', overwrite=True)
            print_flush('Current iteration finished.', 0, rank, **stdout_options)
        comm.Barrier()
コード例 #26
0
    w1_new = w1 - alpha * w1_delta
    b1_new = b1 - alpha * b1_delta
    w2_new = w2 - alpha * w2_delta
    b2_new = b2 - alpha * b2_delta
    new_theta = (w1_new, b1_new, w2_new, b2_new)
    return new_theta


# Compute Gradient
grad_objective = grad(objective)

# Train the Neural Network
epochs = 50
Y_pred = np.argmax(neural_network(D[0], theta), axis=1)
print("Accuracy score before training:",
      accuracy_score(np.nonzero(D[1])[1], Y_pred))
accuScore = []
for i in range(0, epochs):
    print('Epoch: %d' % (i + 1))
    for j in range(0, examples):
        delta = grad_objective(theta, j)
        theta = update_theta(theta, delta, 0.01)
        Y_pred = np.argmax(neural_network(D[0], theta), axis=1)
        accuScore.append(accuracy_score(np.nonzero(D[1])[1], Y_pred))
print("Accuracy score after training:",
      accuracy_score(np.nonzero(D[1])[1], Y_pred))
print(confusion_matrix(np.nonzero(D[1])[1], Y_pred))
print(classification_report(np.nonzero(D[1])[1], Y_pred))
pylab.plot(accuScore)
pylab.show()
コード例 #27
0
def cal_splitvalueI(rating_matrix, user_vectors, current_vector, indices_like,
                    indices_dislike, indices_unknown, K):
    like = rating_matrix[:, indices_like]
    dislike = rating_matrix[:, indices_dislike]
    unknown = rating_matrix[:, indices_unknown]
    like_vector = np.zeros(K)
    dislike_vector = np.zeros(K)
    unknown_vector = np.zeros(K)
    value = 0

    if len(indices_like) > 0:
        # print(indices_like)
        like_vector = cf_item(rating_matrix, user_vectors, current_vector,
                              indices_like, K)
        like_vector = np.array([like_vector for i in range(len(indices_like))])
        pre_like = np.dot(user_vectors, like_vector.T)
        Err_like = pre_like[np.nonzero(like)] - like[np.nonzero(like)]
        value = value + np.dot(Err_like, Err_like)
    # print(value)
    if len(indices_dislike) > 0:
        # print(indices_dislike)
        dislike_vector = cf_item(rating_matrix, user_vectors, current_vector,
                                 indices_dislike, K)
        dislike_vector = np.array(
            [dislike_vector for i in range(len(indices_dislike))])
        pre_dislike = np.dot(user_vectors, dislike_vector.T)
        Err_dislike = pre_dislike[np.nonzero(dislike)] - dislike[np.nonzero(
            dislike)]
        value = value + np.dot(Err_dislike, Err_dislike)
    # print(value)

    if len(indices_unknown) > 0:
        # print(indices_unknown)
        unknown_vector = cf_item(rating_matrix, user_vectors, current_vector,
                                 indices_unknown, K)
        unknown_vector = np.array(
            [unknown_vector for i in range(len(indices_unknown))])
        pre_unknown = np.dot(user_vectors, unknown_vector.T)
        Err_unknown = pre_unknown[np.nonzero(unknown)] - unknown[np.nonzero(
            unknown)]
        value = value + np.dot(Err_unknown, Err_unknown)
    # print(value)

    lkv_l = like_vector[np.nonzero(like_vector)]
    dlkv_l = dislike_vector[np.nonzero(dislike_vector)]
    unkv_l = unknown_vector[np.nonzero(unknown_vector)]
    value = value + lmd_v * (np.dot(lkv_l, lkv_l) + np.dot(dlkv_l, dlkv_l) +
                             np.dot(unkv_l, unkv_l))

    user_l = user_vectors[np.nonzero(user_vectors)]
    value = value + lmd_u * np.dot(user_l, user_l)

    np.random.seed(0)
    num_pair = 20
    num_user, num_item = like.shape
    if num_user * num_item != 0:
        for i in range(num_pair):
            c1, c2 = np.random.randint(0, num_item * num_user, 2)
            u1, i1 = c1 // num_item, c1 % num_item
            u2, i2 = c2 // num_item, c2 % num_item
            if like[u1][i1] > like[u2][i2]:
                diff = np.dot(user_vectors[u1, :].T,
                              like_vector[i1, :]) - np.dot(
                                  user_vectors[u2, :].T, like_vector[i2, :])
                diff = -diff
                value = value + lmd_BPR * np.log(1 + np.exp(diff))

    num_user, num_item = dislike.shape
    if num_user * num_item != 0:
        for i in range(num_pair):
            c1, c2 = np.random.randint(0, num_item * num_user, 2)
            u1, i1 = c1 // num_item, c1 % num_item
            u2, i2 = c2 // num_item, c2 % num_item
            if dislike[u1][i1] > dislike[u2][i2]:
                diff = np.dot(user_vectors[u1, :].T,
                              dislike_vector[i1, :]) - np.dot(
                                  user_vectors[u2, :].T, dislike_vector[i2, :])
                diff = -diff
                value = value + lmd_BPR * np.log(1 + np.exp(diff))

    num_user, num_item = unknown.shape
    if num_user * num_item != 0:
        for i in range(num_pair):
            c1, c2 = np.random.randint(0, num_item * num_user, 2)
            u1, i1 = c1 // num_item, c1 % num_item
            u2, i2 = c2 // num_item, c2 % num_item
            if unknown[u1][i1] > unknown[u2][i2]:
                diff = np.dot(user_vectors[u1, :].T,
                              unknown_vector[i1, :]) - np.dot(
                                  user_vectors[u2, :].T, unknown_vector[i2, :])
                diff = -diff
                value = value + lmd_BPR * np.log(1 + np.exp(diff))
    print(value)
    return value
コード例 #28
0
ファイル: mesh_traversal.py プロジェクト: twbabyduck/mesh_CNN
def get_order(adj_mtx, coords, ix_list, closest_ix, verts):
    """
    Given a list of vertices (at a certain depth away from the center), calculates traversal order
    :param adj_mtx: adjacency matrix of the mesh
    :param coords: list of coordinates for each vertex
    :param ix_list: list of vertices
    :param closest_ix: the starting vertex
    :return: ordered list of vertices
    """
    arr = []
    seen = set(verts)
    arr.append(closest_ix)
    seen.add(closest_ix)
    v = closest_ix
    # find the neighbor
    neigh_list = []

    list_of_lists = []

    if sparse.issparse(adj_mtx):
        nz = adj_mtx.tolil().rows
        for i in ix_list:
            neighs = nz[i]
            list_of_lists.append(neighs)
    else:
        for i in ix_list:
            try:
                neighs = np.nonzero(adj_mtx[i])
            except:
                print("boo")
            neighs = neighs[0]
            list_of_lists.append(neighs)

    ct = 0
    for i in list_of_lists:
        if closest_ix in i:
            if ix_list[ct] not in seen:
                neigh_list.append(ix_list[ct])
        ct += 1

    if len(arr) == len(ix_list):
        return arr

    while len(arr) != len(ix_list):
        if len(neigh_list) >= 2:
            v1 = neigh_list[0]
            v2 = neigh_list[1]
            x1 = coords[v1]
            x2 = coords[v2]
            if x1[0] <= x2[0]:
                v = v1
                arr.append(v)
                seen.add(v)

                neigh_list = []
                ct = 0
                for i in list_of_lists:
                    if v in i and ix_list[ct] not in seen:
                        neigh_list.append(ix_list[ct])
                        seen.add(ix_list[ct])
                    ct += 1
            else:
                v = v2
                arr.append(v)
                seen.add(v)

                neigh_list = []
                ct = 0
                for i in list_of_lists:
                    if v in i and ix_list[ct] not in seen:
                        neigh_list.append(ix_list[ct])
                        seen.add(ix_list[ct])
                    ct += 1

        if len(neigh_list) == 1:
            v = neigh_list[0]
            arr.append(v)
            seen.add(v)

            neigh_list = []
            ct = 0
            for i in list_of_lists:
                if v in i and ix_list[ct] not in seen:
                    neigh_list.append(ix_list[ct])
                    seen.add(ix_list[ct])
                ct += 1

        if len(neigh_list) == 0:
            return arr
コード例 #29
0
def integrate_rkdp5(
    rhs,
    x_eval,
    x_initial,
    y_initial,
    atol=1e-12,
    rtol=0.,
    step_safety_factor=0.9,
    step_update_factor_max=10,
    step_update_factor_min=2e-1,
):
    """
    Integrate using the RKDP5(4) method. For quick intuition, consult [2] and [3].
    See table 5.2 on pp. 178 of [1] or [3] for the Butcher tableau. See pp. 167-169 of [1]
    for automatic step size control and starting step size. Scipy's RK45 implementation
    in python [4] was used as a reference for this implementation.

    References:
    [1] E. Hairer, S.P. Norsett and G. Wanner, Solving Ordinary Differential Equations
    i. Nonstiff Problems. 2nd edition. Springer Series in Computational Mathematics,
    Springer-Verlag (1993)
    [2] https://en.wikipedia.org/wiki/Runge–Kutta_methods
    [3] https://en.wikipedia.org/wiki/Dormand–Prince_method
    [4] https://github.com/scipy/scipy/blob/master/scipy/integrate/_ivp/rk.py
    [5] https://math.stackexchange.com/questions/2947231/how-can-i-derive-the-dense-output-of-ode45/2948244
    
    Arguments:
    atol :: float or array(N) - the absolute tolerance of the component-wise
        local error, i.e. "Atoli" in e.q. 4.10 on pp. 167 of [1]
    rhs :: (x :: float, y :: array(N)) -> dy_dx :: array(N)
        - the right-hand side of the equation dy_dx = rhs(x, y)
        that defines the first order differential equation
    rtol :: float or array(N) - the relative tolerance of the component-wise
        local error, i.e. "Rtoli" in e.q. 4.10 on pp. 167 of [1]
    step_safety_factor :: float - the safety multiplication factor used in the
        step update rule, i.e. "fac" in e.q. 4.13 on pp. 168 of [1]
    step_update_factor_max :: float - the maximum step multiplication factor used in the
        step update rule, i.e. "facmax" in e.q. 4.13 on pp. 168 of [1]
    step_update_factor_min :: float - the minimum step multiplication factor used in the
        step update rule, i.e. "facmin"in e.q.e 4.13 on pp. 168 of [1]
    x_eval :: ndarray (eval_count) - an array of points `x` whose
        corresponding `y` value should be evaluated. It is assumed
        that this list does not contain duplicates, that
        the values are sorted in increasing order, and that
        all values are greater than `x_initial`.
    x_final :: float - the final value of x (inclusive) that concludes the integration interval
    x_initial :: float - the initial value of x (inclusive) that begins the integration interval
    y_initial :: array(N) - the initial value of y

    Returns:
    y_evald :: ndarray (eval_count x N) - an array of points `y` whose
        corresponding `x` value is specified in x_eval
    """
    # Determine how far to integrate to.
    if len(x_eval) == 0:
        raise ValueError("No output was specified.")
    else:
        x_final = x_eval[-1]

    # Compute initial step size per pp. 169 of [1].
    f0 = rhs(x_initial, y_initial)
    d0 = rms_norm(y_initial)
    d1 = rms_norm(f0)
    if d0 < 1e-5 or d1 < 1e-5:
        h0 = 1e-6
    else:
        h0 = 0.01 * d0 / d1
    y1 = y_initial + h0 * f0
    f1 = rhs(x_initial + h0, y1)
    d2 = rms_norm(f1 - f0) / h0
    if anp.maximum(d1, d2) <= 1e-15:
        h1 = anp.maximum(1e-6, h0 * 1e-3)
    else:
        h1 = anp.power(0.01 / anp.maximum(d1, d2), 1 / (P + 1))
    step_current = anp.minimum(100 * h0, h1)

    # Integrate.
    y_eval_list = list()
    x_current = x_initial
    y_current = y_initial
    k1 = f0
    while x_current <= x_final:
        step_rejected = False
        step_accepted = False
        # Repeatedly attempt to move to the next position in the mesh
        # until the step size is adapted such that the local step error
        # is within an acceptable tolerance.
        while not step_accepted:
            # Attempt to step by `step_current`.
            ks, y1, y1h = integrate_rkdp5_step(step_current,
                                               rhs,
                                               x_current,
                                               y_current,
                                               k1=k1)
            # Before the step size is updated for the next step, note where
            # the current attempted step size places us in the mesh.
            x_new = x_current + step_current
            # Compute the local error associated with the attempted step.
            scale = atol + anp.maximum(anp.abs(y1), anp.abs(y1h)) * rtol
            error_norm = rms_norm((y1 - y1h) / scale)

            # If the step is accepted, increase the step size,
            # and move to the next step.
            if error_norm < 1:
                step_accepted = True
                # Avoid division by zero in update.
                if error_norm == 0:
                    step_update_factor = step_update_factor_max
                else:
                    step_update_factor = anp.minimum(
                        step_update_factor_max,
                        step_safety_factor * anp.power(error_norm, ERROR_EXP))
                # Avoid an extraneous update in next step.
                if step_rejected:
                    step_update_factor = anp.minimum(1, step_update_factor)
                step_current = step_current * step_update_factor
            # If the step was rejected, decrease the step size,
            # and reattempt the step.
            else:
                step_rejected = True
                step_update_factor = anp.maximum(
                    step_update_factor_min,
                    step_safety_factor * anp.power(error_norm, ERROR_EXP))
                step_current = step_current * step_update_factor
        #ENDWHILE
        # Interpolate any output points that ocurred in the step.
        x_eval_step_indices = anp.nonzero(
            anp.logical_and(x_current <= x_eval, x_eval <= x_new))[0]
        x_eval_step = x_eval[x_eval_step_indices]
        if len(x_eval_step) != 0:
            y_eval_step = rkdp5_dense(ks, x_current, x_new, x_eval_step,
                                      y_current, y1)
            for y_eval_ in y_eval_step:
                y_eval_list.append(y_eval_)

        # Update the position in the mesh.
        x_current = x_new
        y_current = y1
        k1 = ks[6]  # k[6] = k7
    #ENDWHILE

    return anp.stack(y_eval_list)
コード例 #30
0
ファイル: mesh_traversal.py プロジェクト: twbabyduck/mesh_CNN
def get_neighs_sq2(adj_mtx, i):
    new_row = adj_mtx[i]
    new_row = np.nonzero(new_row)
    verts = new_row[0]
    return verts
コード例 #31
0
ファイル: mesh_traversal.py プロジェクト: twbabyduck/mesh_CNN
def traverse_mesh(coords,
                  faces,
                  center,
                  stride=1,
                  verbose=False,
                  is_sparse=True):
    """
    Calculates the traversal list of all vertices in the mesh
    :param coords: coordinates of the vertices
    :param faces: triplets of vertices for each triangle
    :param center: center vertex
    :param stride: the stride to be covered
    :param verbose: whether to print time after each iteration
    :param is_sparse: whether a sparse implementation is desired
    :return: list of all vertices in the mesh, starting from the center and in order of traversal
    """
    adj_mtx, coords, faces = create_adj_mtx(coords, faces, is_sparse)
    verbose_ctr = 1
    start = time.time()

    if stride == 1:
        vertex = center
        verts = list()

        # level_0
        verts.append(vertex)
        v = vertex

        # find closest point in level 1
        dists = []
        if sparse.issparse(adj_mtx):
            nz = adj_mtx.tolil().rows
            ix_list = nz[v]
        else:
            row = adj_mtx[v]
            ix_list = np.nonzero(row)
            ix_list = ix_list[0]

        for j in ix_list:
            d = get_dist(coords, v, j)
            dists.append(d)
        ix_min = ix_list[dists.index(min(dists))]
        closest_ix = ix_min

        # levels_>=1
        if sparse.issparse(adj_mtx):
            l = adj_mtx.shape[0]
        else:
            l = len(adj_mtx[0])
        # until all vertices are seen
        while len(verts) <= 0.95 * l:
            # this is the closest vertex of the new level
            # find the ordering of the level
            if verbose:
                print("Iteration {}: {}".format(verbose_ctr,
                                                time.time() - start))
            verbose_ctr = verbose_ctr + 1
            arr = get_order(adj_mtx, coords, ix_list, closest_ix, verts)
            for i in arr:
                if i not in verts:
                    verts.append(i)
            # get next level: for each in ix_list, get neighbors that are not in <verts>, then add them to the new list
            next_list = []
            for j in ix_list:
                if sparse.issparse(adj_mtx):
                    new_row = nz[j]
                else:
                    new_row = adj_mtx[j]
                    new_row = np.nonzero(new_row)
                    new_row = new_row[0]

                for k in new_row:
                    if k not in verts:
                        next_list.append(k)
            next_list = list(set(next_list))
            if len(next_list) == 0:
                continue
            # find starting point of next level using line eq
            c1 = coords[vertex]
            c2 = coords[closest_ix]
            line_dists = []
            for j in next_list:
                c3 = coords[j]
                line_dist = LA.norm(np.cross(c2 - c1, c1 - c3)) / LA.norm(
                    c2 - c1)  # not exactly sure of this
                line_dists.append(line_dist)
            ix_list = next_list
            closest_ix = next_list[line_dists.index(min(line_dists))]
        return verts

    else:  # multiple stride case

        vertex = center
        verts = list()

        # level_0
        verts.append(vertex)
        v = vertex

        seen = list()
        seen.append(v)

        if sparse.issparse(adj_mtx):
            nz = adj_mtx.tolil().rows
            ix_list = nz[v]
        else:
            row = adj_mtx[v]
            ix_list = np.nonzero(row)
            ix_list = ix_list[0]

        dists = []
        for j in ix_list:
            d = get_dist(coords, v, j)
            dists.append(d)
        ix_min = ix_list[dists.index(min(dists))]
        closest_ix = ix_min

        add_to_verts = False
        ctr = 1
        # levels_>=1
        if sparse.issparse(adj_mtx):
            l = adj_mtx.shape[0]
        else:
            l = len(adj_mtx[0])
        while len(seen) != l:  # until all vertices are seen
            # this is the closest vertex of the new level
            # find the ordering of the level
            arr = get_order(adj_mtx, coords, ix_list, closest_ix, seen)
            seen = seen + arr

            if add_to_verts:  # add only every other level to the traversal list
                temp_arr = arr[::stride]
                verts = verts + temp_arr
            # get next level: for each in ix_list, get neighbors that are not in <verts>, then add them to the new list
            ctr = ctr + 1
            if ctr % stride == 0:
                add_to_verts = True
            else:
                add_to_verts = False
            next_list = []
            for j in ix_list:
                if sparse.issparse(adj_mtx):
                    nz = adj_mtx.tolil().rows
                    new_row = nz[j]
                else:
                    new_row = adj_mtx[j]
                    new_row = np.nonzero(new_row)
                    new_row = new_row[0]

                for k in new_row:
                    if k not in seen:
                        next_list.append(k)
            next_list = list(set(next_list))
            if len(next_list) == 0:
                continue
            # find starting point of next level using line eq
            c1 = coords[vertex]
            c2 = coords[closest_ix]
            line_dists = []
            for j in next_list:
                c3 = coords[j]
                line_dist = LA.norm(np.cross(c2 - c1, c1 - c3)) / LA.norm(
                    c2 - c1)  # not exactly sure of this
                line_dists.append(line_dist)
            ix_list = next_list
            closest_ix = next_list[line_dists.index(min(line_dists))]
        return verts
コード例 #32
0
    w1_new = w1 - alpha * w1_delta
    b1_new = b1 - alpha * b1_delta
    w2_new = w2 - alpha * w2_delta
    b2_new = b2 - alpha * b2_delta
    new_theta = (w1_new, b1_new, w2_new, b2_new)
    return new_theta


# Compute Gradient
grad_objective = grad(objective)

# Train the Neural Network
epochs = 50
Y_pred = np.argmax(neural_network(D[0], theta), axis=1)
print("Accuracy score before training:",
      sklearn.metrics.accuracy_score(np.nonzero(D[1])[1], Y_pred))
accuScore = []
for i in range(0, epochs):
    print('Epoch: %d' % (i + 1))
    for j in range(0, examples):
        delta = grad_objective(theta, j)
        theta = update_theta(theta, delta, 0.3)
        Y_pred = np.argmax(neural_network(D[0], theta), axis=1)
        accuScore.append(
            sklearn.metrics.accuracy_score(np.nonzero(D[1])[1], Y_pred))
print("Accuracy score after training:",
      sklearn.metrics.accuracy_score(np.nonzero(D[1])[1], Y_pred))
print(sklearn.metrics.confusion_matrix(np.nonzero(D[1])[1], Y_pred))
print(sklearn.metrics.classification_report(np.nonzero(D[1])[1], Y_pred))
pylab.plot(accuScore)
pylab.show()