def odf(self, vertices=None, cache=None): """Predict the ODF at the given vertices. """ if vertices is None: self._odf_kernel_matrix = cache._odf_kernel_matrix else: odf_theta, odf_phi = cart2sphere(*vertices.T)[1:] X = kernel_matrix(odf_theta, odf_phi, self.model.kernel_theta, self.model.kernel_phi, kernel=even_kernel, N=self.model.sh_order) #attempt to append iso col and spherical harmonic cols to X: append = sh(odf_theta, odf_phi, np.size(odf_theta)) X = np.hstack((X, append)) self._odf_kernel_matrix = X #return np.dot(self._odf_kernel_matrix, self.beta) + \ # self.intercept return self._odf_kernel_matrix, self.beta, self.intercept
def __init__(self, bvals, gradients, sh_order=8, qp=132, loglog_tf=True): """Sparse kernel model. Parameters ---------- bvals : 1-D ndarray B-values. gradients : (N, 3) ndarray Gradient directions, xyz. sh_order : int Highest order of spherical harmonic fit. qp : {72, 132, 492} Number of kernels used to represent the signal. loglog_tf : bool Whether to perform ``log(-log(.))`` on the signal before fitting. In theory, this gives a better representation of the ODF (but does predict back the original signal). Also, it seems not to work well for low b-values (<= 1500). """ where_dwi = bvals > 0 self.qp = qp self.sh_order = sh_order self.loglog_tf = loglog_tf self.gradient_theta, self.gradient_phi = \ cart2sphere(*gradients[where_dwi].T)[1:] self.kernel_theta, self.kernel_phi, _ = quadrature_points(N=qp) self.X = np.asfortranarray( kernel_matrix(self.gradient_theta, self.gradient_phi, self.kernel_theta, self.kernel_phi, kernel=inv_funk_radon_even_kernel, N=self.sh_order)) #attempt to append iso col and spherical harmonic cols to X: P2 = sp.special.legendre(2) append = sh(self.gradient_theta, self.gradient_phi, np.size(self.gradient_theta)) append[:,1:] = append[:,1:]/(-12*np.pi*P2(0)) #print append, "append" self.X = np.hstack((self.X, append))