Nothing
##
## p r o c r u s t e s . R Procrustes Problem
##
procrustes <- function(A, B) {
stopifnot(is.numeric(A), is.numeric(B))
if (!is.matrix(A) || !is.matrix(B))
stop("Arguments 'A' and 'B' must be numeric matrices.")
if (any(dim(A) != dim(B)))
stop("Matrices 'A' and 'B' must be of the same size.")
C <- t(B) %*% A
Svd <- svd(C) # singular value decomposition
U <- Svd$u
S <- diag(Svd$d)
V <- Svd$v
Q <- U %*% t(V)
P <- B %*% Q
R <- A - P;
r <- sqrt(Trace(t(R) %*% R)) # Frobenius norm: Norm(A - P)
return(list(P = P, Q = Q, d = r))
}
kabsch <- function(A, B, w = NULL) {
stopifnot(is.numeric(A), is.numeric(B))
if ( !is.matrix(A) || !is.matrix(B) )
stop("Arguments 'A' and 'B' must be numeric matrices.")
if ( any(dim(A) != dim(B)) )
stop("Matrices 'A' and 'B' must be of the same size.")
D <- nrow(A) # space dimension
N <- ncol(A) # number of points
if (is.null(w)) {
w <- matrix(1/N, nrow = N, ncol = 1) # weights as column vector
} else {
if (!is.numeric(w) || length(w) != N)
stop("Argument 'w' must be a (column) vector of length ncol(A).")
}
p0 <- A %*% w # the centroid of A
q0 <- B %*% w # the centroid of B
v1 <- ones(1,N) # row vector of N ones
A <- A - p0 %*% v1 # translating A to center the origin
B <- B - q0 %*% v1 # translating B to center the origin
Pdm <- zeros(D,N)
for (i in 1:N) Pdm[, i] <- w[i] * A[, i]
C <- Pdm %*% t(B)
Svd <- svd(C) # singular value decomposition
V <- Svd$u
S <- diag(Svd$d)
W <- Svd$v
I <- eye(D)
# more numerically stable than using (det(C) < 0)
if (det(V %*% t(W)) < 0) I[D, D] <- -1
U <- W %*% I %*% t(V)
R <- q0 - U %*% p0
Diff <- U %*% A - B # A, B already centered
lrms <- 0
for (i in 1:N) lrms <- lrms + w[i] * t(Diff[, i]) %*% Diff[, i]
lrms <- sqrt(lrms)
return(list(U = U, R = R, d = lrms))
}
Any scripts or data that you put into this service are public.
Add the following code to your website.
For more information on customizing the embed code, read Embedding Snippets.