- データレコードが行列状になっているときに、重複行を見つけて、ダブっている分を除いて、1行分にして出すのがunique()
- 今、ダブっているレコードは1行残らず、破棄したい
- unique()関数は、上からスキャンして、初出はTRUE、既出分とダブったらFALSEを返す関数 duplicate()を基準にしているので、スキャンを上下の2方向からやって、どちらでもTRUEな行は、重複に関わらない行
my.onlyone <- function(x){
n <- length(x[,1])
a <- !duplicated(x)
b <- !duplicated(x[n:1,])[n:1]
return(x[a & b,])
}
x <- matrix(c(0,0,0,1,0,1,1,1),byrow=TRUE,ncol=2)
my.onlyone(x)
- これを使って、『図形』がブロックで出来ているときに、内部点・内部面などを取り除いて表面要素だけにすることができるだろう
Vox.list <- as.matrix(expand.grid(0:2,0:2,0:2))
my.vox.faces <- function(xyz){
rbind(c(xyz,1),c(xyz,2),c(xyz,3),c(xyz+c(1,0,0),2),c(xyz+c(0,1,0),3),c(xyz+c(0,0,1),1))
}
my.face.nodes <- function(xyzw){
xyz <- xyzw[1:3]
w <- xyzw[4]
if(w==1){
ret <- rbind(xyz,xyz+c(1,0,0),xyz+c(0,1,0),xyz+c(1,1,0))
}else if(w==2){
ret <- rbind(xyz,xyz+c(0,1,0),xyz+c(0,0,1),xyz+c(0,1,1))
}else{
ret <- rbind(xyz,xyz+c(0,0,1),xyz+c(1,0,0),xyz+c(1,0,1))
}
return(ret)
}
my.onlyone <- function(x){
n <- length(x[,1])
a <- !duplicated(x)
b <- !duplicated(x[n:1,])[n:1]
return(x[a & b,])
}
my.vox.surface <- function(Vlist){
faces <- matrix(0,0,4)
for(i in 1:length(Vlist[,1])){
faces <- rbind(faces,my.vox.faces(Vlist[i,]))
}
return(my.onlyone(faces))
}
faces <- my.vox.surface(Vox.list)
my.surface.nodes <- function(faces){
vs <- matrix(0,0,3)
for(i in 1:length(faces[,1])){
vs <- rbind(vs,my.face.nodes(faces[i,]))
}
return(unique(vs))
}
nodes <- my.surface.nodes(faces)
library(rgl)
plot3d(nodes)