def InnerProduct(self,vector,other): """Innerproduct for vectors""" if vector.GetSpace()==other.GetSpace(): from Numeric import matrixmultiply,transpose # (v,o)=(v_coor^T*basis^T*basis*o_coor) metric=matrixmultiply(self.GetBasis(),transpose(self.GetBasis())) return dot(vector.GetCoordinates(),matrixmultiply(metric,other.GetCoordinates())) else: raise ValueError, 'Innerproduct of two vectors in different vector space not implemented'
def InnerProduct(self, vector, other): """Innerproduct for vectors""" if vector.GetSpace() == other.GetSpace(): from Numeric import matrixmultiply, transpose # (v,o)=(v_coor^T*basis^T*basis*o_coor) metric = matrixmultiply(self.GetBasis(), transpose(self.GetBasis())) return dot(vector.GetCoordinates(), matrixmultiply(metric, other.GetCoordinates())) else: raise ValueError, 'Innerproduct of two vectors in different vector space not implemented'
def corrcoef(*args): """ corrcoef(X) where X is a matrix returns a matrix of correlation coefficients for each row of X. corrcoef(x,y) where x and y are vectors returns the matrix or correlation coefficients for x and y. Numeric arrays can be real or complex The correlation matrix is defined from the covariance matrix C as r(i,j) = C[i,j] / (C[i,i]*C[j,j]) """ if len(args) == 2: X = transpose(array([args[0]] + [args[1]])) elif len(args == 1): X = args[0] else: raise RuntimeError, 'Only expecting 1 or 2 arguments' C = cov(X) d = resize(diagonal(C), (2, 1)) r = divide(C, sqrt(matrixmultiply(d, transpose(d))))[0, 1] try: return r.real except AttributeError: return r
def render(self): s = self.svgDrawing if not s: return x, y, z = self.body.getPosition() modelview = glGetDoublev(GL_MODELVIEW_MATRIX) projection = glGetDoublev(GL_PROJECTION_MATRIX) viewport = glGetIntegerv(GL_VIEWPORT) # calculate the z coordinate m = transpose(reshape(modelview, (4, 4))) wz = -matrixmultiply(m, reshape((x, y, z, 1), (4, 1)))[2][0] # don't draw anything if we're behind the viewer if wz < 0.1: return # calculate the screen-space x and y coordinates x, y, z = gluProject(x, y, z, modelview, projection, viewport) scale = self.scale / wz s.transform.reset() s.transform.translate(x, y) s.transform.scale(scale, -scale) s.transform.rotate(self.rotation) s.draw()
def eigenvector_for_largest_eigenvalue(matrix): """Returns eigenvector corresponding to largest eigenvalue of matrix. Implements a numerical method for finding an eigenvector by repeated application of the matrix to a starting vector. For a matrix A the process w(k) <-- A*w(k-1) converges to eigenvector w with the largest eigenvalue. Because distance matrix D has all entries >= 0, a theorem due to Perron and Frobenius on nonnegative matrices guarantees good behavior of this method, excepting degenerate cases where the iteration oscillates. For distance matrices a remedy is to add the identity matrix to A, permitting the iteration to converge to the eigenvector. (From Sander and Schneider (1991), and Vingron and Sibbald (1993)) Note: Only works on square matrices. """ #always add the identity matrix to avoid oscillating behavior matrix = matrix + identity(len(matrix)) #v is a random vector (chosen as the normalized vector of ones) v = ones(len(matrix))/len(matrix) #iterate until convergence for i in range(1000): new_v = matrixmultiply(matrix,v) new_v = new_v/sum(new_v) #normalize if sum(map(abs,new_v-v)) > 1e-9: v = new_v #not converged yet continue else: #converged break return new_v
def _alpha(self,obsIndices): """ computes forward values""" B = self.B A = self.A alpha = [B[obsIndices[0]] * self.pi] # (19) for o in obsIndices[1:]: alpha.append(matrixmultiply(alpha[-1],A)*B[o]) # (20) return alpha
def rotate(self, angle): m = identity(3, typecode = Float) s = sin(angle) c = cos(angle) m[0, 0] = c m[0, 1] = -s m[1, 0] = s m[1, 1] = c self.matrix = matrixmultiply(self.matrix, m)
def rotate(self, angle): m = identity(3, typecode=Float) s = sin(angle) c = cos(angle) m[0, 0] = c m[0, 1] = -s m[1, 0] = s m[1, 1] = c self.matrix = matrixmultiply(self.matrix, m)
def get_transformed(self): "Get the transformed coordinate set." if self.coords is None or self.reference_coords is None: raise Exception, "No coordinates set." if self.rot is None: raise Exception, "Nothing superimposed yet." if self.transformed_coords is None: self.transformed_coords=matrixmultiply(self.coords, self.rot)+self.tran return self.transformed_coords
def _beta(self,obsIndices,scale_factors=None): """ computes backward values""" B = self.B A = self.A scale_factors = scale_factors or list(ones(len(obsIndices),Float)) beta = [ones(self.N,Float)*scale_factors[-1]] # (24) for t in range(len(obsIndices)-2,-1,-1): beta.append(matrixmultiply(A,(1./scale_factors[t])*B[obsIndices[t+1]]*beta[-1])) # (25) beta.reverse() return beta
def __rmul__(self,other): import copy from Numeric import asarray,matrixmultiply a=copy.copy(self) if asarray(other).shape == (): a.SetBasis(other*self.GetBasis()) elif asarray(other).shape == self.GetBasis().shape: a.SetBasis(matrixmultiply(other,self.GetBasis())) else: raise ValueError, 'matrices are not aligned' return a
def run(self): "Superimpose the coordinate sets." if self.coords is None or self.reference_coords is None: raise Exception, "No coordinates set." coords=self.coords reference_coords=self.reference_coords # center on centroid av1=sum(coords)/self.n av2=sum(reference_coords)/self.n coords=coords-av1 reference_coords=reference_coords-av2 # correlation matrix a=matrixmultiply(transpose(coords), reference_coords) u, d, vt=singular_value_decomposition(a) self.rot=transpose(matrixmultiply(transpose(vt), transpose(u))) # check if we have found a reflection if determinant(self.rot)<0: vt[2]=-vt[2] self.rot=transpose(matrixmultiply(transpose(vt), transpose(u))) self.tran=av2-matrixmultiply(av1, self.rot)
def __rmul__(self, other): import copy from Numeric import asarray, matrixmultiply a = copy.copy(self) if asarray(other).shape == (): a.SetBasis(other * self.GetBasis()) elif asarray(other).shape == self.GetBasis().shape: a.SetBasis(matrixmultiply(other, self.GetBasis())) else: raise ValueError, 'matrices are not aligned' return a
def _alpha_scaled(self,obsIndices): """ computes forward values""" B = self.B A = self.A alpha_t = B[obsIndices[0]] * self.pi # (19) scaling_factors = [sum(alpha_t)] alpha_scaled = [alpha_t/scaling_factors[-1]] for o in obsIndices[1:]: alpha_t = matrixmultiply(alpha_scaled[-1],A)*B[o] # (92a) scaling_factors.append(sum(alpha_t)) alpha_scaled.append(alpha_t/scaling_factors[-1]) # (92b) return alpha_scaled,scaling_factors
def applyAttributes(self, attrs, key="transform"): transform = attrs.get(key) if transform: m = re.match(r"translate\(\s*(.+?)\s*,(.+?)\s*\)", transform) if m: dx, dy = [float(c) for c in m.groups()] self.matrix[0, 2] += dx self.matrix[1, 2] += dy m = re.match(r"matrix\(\s*" + "\s*,\s*".join(["(.+?)"] * 6) + r"\s*\)", transform) if m: e = [float(c) for c in m.groups()] e = [e[0], e[2], e[4], e[1], e[3], e[5], 0, 0, 1] m = reshape(e, (3, 3)) self.matrix = matrixmultiply(self.matrix, m)
def savitzky_golay(window_size=None,order=2): if window_size is None: window_size = order + 2 if window_size % 2 != 1 or window_size < 1: raise TypeError("window size must be a positive odd number") if window_size < order + 2: raise TypeError("window size is too small for the polynomial") # A second order polynomial has 3 coefficients order_range = range(order+1) half_window = (window_size-1)//2 B = array( [ [k**i for i in order_range] for k in range(-half_window, half_window+1)] ) # -1 # [ T ] T # [ B * B ] * B M = matrixmultiply( inverse( matrixmultiply(transpose(B), B)), transpose(B) ) return M
def applyAttributes(self, attrs, key = "transform"): transform = attrs.get(key) if transform: m = re.match(r"translate\(\s*(.+?)\s*,(.+?)\s*\)", transform) if m: dx, dy = [float(c) for c in m.groups()] self.matrix[0, 2] += dx self.matrix[1, 2] += dy m = re.match(r"matrix\(\s*" + "\s*,\s*".join(["(.+?)"] * 6) + r"\s*\)", transform) if m: e = [float(c) for c in m.groups()] e = [e[0], e[2], e[4], e[1], e[3], e[5], 0, 0, 1] m = reshape(e, (3, 3)) self.matrix = matrixmultiply(self.matrix, m)
def arbitaryRotation(coord, angle, axis): """arbitaryRotation(coord, angle, vector) --> rotates point by angle around vector !!NB!! the axis is always through the origin!! must do offset first""" u, v, w = normalise(axis) oldCoord = array([coord[0], coord[1], coord[2]]) cth = cos(angle/180.*pi) sth = sin(angle/180.*pi) R = array([[cth + u**2*(1-cth), -w*sth+u*v*(1-cth), v*sth+u*w*(1-cth)], [ w*sth+u*v*(1-cth), cth+v**2*(1-cth), -u*sth+v*w*(1-cth)], [-v*sth+u*w*(1-cth), u*sth+v*w*(1-cth), cth+w**2*(1-cth)]]) newCoord = matrixmultiply(R,oldCoord) return [newCoord[0], newCoord[1], newCoord[2]]
def transform(self, rot, tran): """ Apply rotation and translation to the atomic coordinates. Example: >>> rotation=rotmat(pi, Vector(1,0,0)) >>> translation=array((0,0,1), 'f') >>> atom.transform(rotation, translation) @param rot: A right multiplying rotation matrix @type rot: 3x3 Numeric array @param tran: the translation vector @type tran: size 3 Numeric array """ self.coord=matrixmultiply(self.coord, rot)+tran
def rotmat(p,q): """ Return a (left multiplying) matrix that rotates p onto q. Example: >>> r=rotmat(p,q) >>> print q, p.left_multiply(r) @param p: moving vector @type p: L{Vector} @param q: fixed vector @type q: L{Vector} @return: rotation matrix that rotates p onto q @rtype: 3x3 Numeric array """ rot=matrixmultiply(refmat(q, -p), refmat(p, -p)) return rot
def refmat(p,q): """ Return a (left multiplying) matrix that mirrors p onto q. Example: >>> mirror=refmat(p,q) >>> qq=p.left_multiply(mirror) >>> print q, qq # q and qq should be the same @type p,q: L{Vector} @return: The mirror operation, a 3x3 Numeric array. """ p.normalize() q.normalize() if (p-q).norm()<1e-5: return eye(3) pq=p-q pq.normalize() b=pq.get_array() b.shape=(3, 1) i=eye(3) ref=i-2*matrixmultiply(b, transpose(b)) return ref
def transform(self, transform): self.matrix = matrixmultiply(self.matrix, transform.matrix)
# start! sup=SVDSuperimposer() # set the coords # y will be rotated and translated on x sup.set(x, y) # do the lsq fit sup.run() # get the rmsd rms=sup.get_rms() # get rotation (right multiplying!) and the translation rot, tran=sup.get_rotran() # rotate y on x y_on_x1=matrixmultiply(y, rot)+tran # same thing y_on_x2=sup.get_transformed() print y_on_x1 print print y_on_x2 print print "%.2f" % rms
def scale(self, sx, sy): m = identity(3, typecode=Float) m[0, 0] = sx m[1, 1] = sy self.matrix = matrixmultiply(self.matrix, m)
def applyTransform(self, transform): m = matrixmultiply(transform.matrix, self.transform.matrix) self.gradientDesc.SetMatrix(transform.getGMatrix(m))
def scale(self, sx, sy): m = identity(3, typecode = Float) m[0, 0] = sx m[1, 1] = sy self.matrix = matrixmultiply(self.matrix, m)
def right_multiply(self, matrix): "Return Vector=Vector x Matrix" a=matrixmultiply(self._ar, matrix) return Vector(a)
def left_multiply(self, matrix): "Return Vector=Matrix x Vector" a=matrixmultiply(matrix, self._ar) return Vector(a)
def ACL(tree): """Returns a normalized dictionary of sequence weights {seq_id: weight} tree: a PhyloNode object The ACL method is named after Altschul, Carroll and Lipman, who published a paper on sequence weighting in 1989. The ACL method is based on an idea of Felsenstein (1973). Imagine electrical current flows from the root of the tree down the edges and out the leaves. If the edge lengths are proportional to their electrical resistances, current flowing out each leaf equals the leaf weight. The first step in the calculation of the weight vector is calculating a variance-covariance matrix. The variance of a leaf is proportional to the distance from the root to that leaf. The covariance of two leaves is proportional to the distance from the root to the last common ancestor of the two leaves. The second step in the calculation results in a vector of weights. Suppose there are n leaves on the tree. Let i be the vector of size n, all of whose elements are 1.0. The weight vector is calculated as: w = (inverse(M)*i)/(transpose(i)*inverse(M)*i) See Altschul 1989 """ #clip branch lengths to avoid error due to negative or zero branch lengths _clip_branch_lengths(tree) #get a list of sequence IDs (in the order that the tree will be traversed) seqs = [] for n in tree.TerminalDescendants: seqs.append(n.Data) #initialize the variance-covariance matrix m = zeros([len(seqs),len(seqs)],Float64) #calculate (co)variances #variance of a node is defined as the distance from the root to the leaf #covariance of two nodes is defined as the distance from the root to the #last common ancestor of the two leaves. for x in tree.TerminalDescendants: for y in tree.TerminalDescendants: idx_x = seqs.index(x.Data) idx_y = seqs.index(y.Data) if idx_x == idx_y: m[idx_x,idx_y] = x.distance(tree) else: lca = x.lastCommonAncestor(y) dist_lca_root = lca.distance(tree) m[idx_x,idx_y] = dist_lca_root m[idx_y,idx_x] = dist_lca_root #get the inverse of the variance-covariance matrix inv = inverse(m) #build vector i (vector or ones, length = # of leaves in the tree) i = ones(len(seqs),Float64) numerator = matrixmultiply(inv, i) denominator = matrixmultiply(matrixmultiply(transpose(i),inv),i) weight_vector = numerator/denominator #return a Weights object (is dict {seq_id: weight}) return Weights(dict(zip(seqs,weight_vector)))
def iagaussian(s,mu,sigma): """ o Purpose Generate a 2D Gaussian image. o Synopsis g = iagaussian(s,mu,sigma) o Input s: [rows columns] mu: Mean vector. 2D point (x;y). Point of maximum value. sigma: covariance matrix (square). [ Sx^2 Sxy; Syx Sy^2] o Output g: o Description A 2D Gaussian image is an image with a Gaussian distribution. It can be used to generate test patterns or Gaussian filters both for spatial and frequency domain. The integral of the gaussian function is 1.0. o Examples import Numeric f = iagaussian([8,4], [3,1], [[1,0],[0,1]]) print Numeric.array2string(f, precision=4, suppress_small=1) g = ianormalize(f, [0,255]).astype(Numeric.UnsignedInt8) print g f = iagaussian(100, 50, 10*10) g = ianormalize(f, [0,1]) g,d = iaplot(g) showfig(g) f = iagaussian([50,50], [25,10], [[10*10,0],[0,20*20]]) g = ianormalize(f, [0,255]).astype(Numeric.UnsignedInt8) iashow(g) """ from Numeric import asarray,product,arange,NewAxis,transpose,matrixmultiply,reshape,concatenate,resize,sum,zeros,Float,ravel,pi,sqrt,exp from LinearAlgebra import inverse,determinant if type(sigma).__name__ in ['int', 'float', 'complex']: sigma = [sigma] s, mu, sigma = asarray(s), asarray(mu), asarray(sigma) if (product(s) == max(s)): x = arange(product(s)) d = x - mu if len(d.shape) == 1: tmp1 = d[:,NewAxis] tmp3 = d else: tmp1 = transpose(d) tmp3 = tmp1 if len(sigma) == 1: tmp2 = 1./sigma else: tmp2 = inverse(sigma) k = matrixmultiply(tmp1, tmp2) * tmp3 else: aux = arange(product(s)) x, y = iaind2sub(s, aux) xx = reshape(concatenate((x,y)), (2, product(x.shape))) d = transpose(xx) - resize(reshape(mu,(len(mu),1)), (s[0]*s[1],len(mu))) if len(sigma) == 1: tmp = 1./sigma else: tmp = inverse(sigma) k = matrixmultiply(d, tmp) * d k = sum(transpose(k)) g = zeros(s, Float) aux = ravel(g) if len(sigma) == 1: tmp = sigma else: tmp = determinant(sigma) aux[:] = 1./(2*pi*sqrt(tmp)) * exp(-1./2 * k) return g