# # distAssoc package # Copyright (C) 2005 Jan de Leeuw # UCLA Department of Statistics, Box 951554, Los Angeles, CA 90095-1554 # # This program is free software; you can redistribute it and/or modify # it under the terms of the GNU General Public License as published by # the Free Software Foundation; either version 2 of the License, or # (at your option) any later version. # # This program is distributed in the hope that it will be useful, # but WITHOUT ANY WARRANTY; without even the implied warranty of # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the # GNU General Public License for more details. # # You should have received a copy of the GNU General Public License # along with this program; if not, write to the Free Software # Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA. # ################################################################### # # version 0.0.01, 2005-11-13 # version 0.0.02, 2005-11-14 (this one actually works) # version 0.0.03, 2005-11-15 (inner products added) # version 0.0.04, 2005-11-15 (single mode analysis added) # version 0.0.05, 2005-11-15 (changed deviance to chi-square) # version 0.0.06, 2005-11-15 (separate bias estimation with IPF) # version 0.0.07, 2005-11-15 (separate versions for one and two modes) # version 0.0.08, 2005-11-16 (plot labels, plot names, normalize bias) # version 0.0.09, 2005-11-18 (alternative majorization for Poisson Likelihood) # version 0.0.10, 2005-11-20 (missing data in Poisson likelihood) # version 0.0.11, 2005-11-20 (smacofSym fixed to handle negative targets) # version 0.0.12, 2006-02-01 (fixed distAltOne) # version 0.0.13, 2006-02-06 (small bugfixes) # version 0.1.00, 2006-02-06 (switched completely to Poisson likelihoods) # version 0.1.01, 2006-02-06 (use elegant instead of alscal for squared distances) # version 0.2.00, 2006-02-09 (added quasi-symmetry/quasi-independence for hollow matrices) # version 0.2.01, 2006-02-09 (use elegantRect for off-diagonal case) # version 0.3.00, 2006-02-09 (added linear restrictions in the symmetric case) # version 0.4.00, 2006-02-18 (added distAssColPart to deal with column partitioning) # version 0.4.01, 2006-02-18 (small speedup by moving calculations out of loop) # version 0.4.02, 2006-02-18 (added voronoi plots to distAssColPart) # version 0.4.03, 2006-02-18 (nasty bug with indexing fixed in distAssColPart) # version 0.4.04, 2006-02-20 (various speedsups, separate options for row and column effects) # version 0.4.05, 2006-02-20 (share some common IO routines) # version 0.4.06, 2006=03-07 (added license information) # require("smacof") require("elegant") distAssOne<-function( freq, # data (single square matrix of frequencies) ndim=2, # dimensionality (default 2) outeps=1e-4, ineps=1e-4, reg=1e-6, rule="dist2", z="none", bias=c(TRUE,TRUE), outmax=500, inmax=1, theplot=TRUE) { name<-deparse(substitute(freq)) nrow<-dim(freq)[1]; ncol<-dim(freq)[2]; itel<-1; freq<-as.matrix(freq) mis<-ifelse(is.na(freq),0,1); dmis<-ifelse(is.na(freq),0,freq) b<-rep(1,ncol); a<-rep(1,nrow) rd<-rowSums(dmis); cd<-colSums(dmis) e<-log(ifelse(dmis==0,1,dmis)); dmin<-2*(sum(dmis)-sum(dmis*e)) e<--.5*(e-outer(rowSums(e)/ncol,colSums(e)/nrow,"+")+(sum(e)/(ncol*nrow))) z<-svd(e,nu=ndim,nv=0); x<-z$u; x<-crossprod(e,x) if (rule=="dist") phi<--distSym(x,reg) else phi<--dist2Sym(x) ep<-exp(phi); lb<-ep; pdev<-(2*(sum(mis*lb)-sum(dmis*log(lb))))-dmin repeat { if (bias[1]) a<-rd/as.vector(((mis*ep)%*%b)) if (bias[2]) b<-cd/as.vector((a%*%(mis*ep))) ab<-outer(a,b); lb<-ab*ep devab<-(2*(sum(mis*lb)-sum(dmis*log(lb))))-dmin targ<--((phi)+((dmis-lb)/ab)); ww<-mis*ab; wt<-ww*targ; www<-ww+t(ww) targ<-(wt+t(wt))/ifelse(www==0,1,www) if (rule=="dist") uu<-smacofSym(targ,w=www,init=x,p=ndim,itmax=inmax,reg=reg,verbose=FALSE) else uu<-elegantSym(targ,w=www,init=x,p=ndim,itmax=inmax,verbose=FALSE) x<-uu$x if (rule=="dist") phi<--distSym(x,reg) else phi<--dist2Sym(x) ep<-exp(phi); lb<-ab*ep; devxy<-(2*(sum(mis*lb)-sum(dmis*log(lb))))-dmin writeIter(itel,pdev,devab,devxy) if ((itel == outmax) || ((pdev-devxy)