zenplot: Zenplot: Zigzag Expanded Navigation Plots

Description Usage Arguments Value Author(s) See Also Examples

Description

Construct and draw a zigzag expanded navigation plot for a graphical exploratory analysis of a path of variables.

Usage

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
unfold(nVars, turns=NULL, n2dcol=5,
       method=c("tidy", "double.zigzag", "single.zigzag"),
       last1d=TRUE, width1d=1, width2d=10)
zenplot(x, scale=c("columnwise", "rowwise", "all", "pobs", "none"),
        turns=NULL, n2dcol=5,
        method=c("tidy", "double.zigzag", "single.zigzag"),
        pkg=c("graphics", "grid"),
        plot1d=c("rug", "points", "jitter", "density", "boxplot", "hist",
                 "label", "arrow", "rect", "lines"),
        plot2d=c("points", "density", "axes", "label", "arrow", "rect"),
        last1d=TRUE, width1d=NULL, width2d=NULL,
        par.list=list(mar=rep(0, 4), oma=rep(0.6, 4)),
        vp1d=NULL, vp2d=NULL, vp=viewport(width=unit(0.96, "npc"),
                                          height=unit(0.96, "npc")),
        draw=TRUE, ...)

Arguments

x

(n,d)-matrix (or (n,d)-data.frame) containing the data.

scale

A function applied to x for scaling to [0,1] (the default plot region) or a character string indicating the scaling method (in which case scale01() is called). The behavior for scale="none" is as follows: If x is in [0,1], no scaling is done. If not, then plot1d and plot2d have to be functions which have to take care of proper scaling.

nVars

The number of variables. zenplot() calls unfold() with nVars=ncol(x).

turns

A character vector of length two times the number of variables to be plotted minus 1 consisting of "d", "u", "r" or "l".

n2dcol

The number of columns containing bivariate (2d) plots.

method

The type of zigzag plot (a character). Available are:

tidy:

A more tidied-up double.zigzag (slightly more compact placement of plots towards the end).

double.zigzag:

A zigzag plot in the form of a flipped “S”. Along this path, the plots are placed in the form of an “S” which is rotated counterclockwise by 90 degrees.

single.zigzag:

A zigzag plot in the form of a flipped “S”.

Note that method is ignored if turns are provided.

plot1d

A function in one variable returning a one-dimensional plot constructed with package pkg (typically a grob constructed with pkg="grid"). Alternatively, a character string indicating which of the provided default plots should be used. plot1d can also be NULL in which case no plot is constructed (for pkg="grid", nullGrob() is returned).

plot2d

A function in two variables returning a two-dimensional plot constructed with package pkg (typically a grob constructed with pkg="grid"). Alternatively, a character string indicating which of the provided default plots should be used. plot2d can also be NULL in which case no plot is constructed (for pkg="grid", nullGrob() is returned).

pkg

The R package used for plotting (depends on how the functions plot1d and plot2d were constructed; the user is responsible for choosing the appropriate package among the currently supported ones).

last1d

A logical indicating whether the last one-dimensional plot shall be included.

draw

A logical indicating whether a plot is created.

width1d

Graphical parameter giving the width of univariate (1d) plots. If NULL a default is chosen.

width2d

Graphical parameter giving the width of bivariate (2d) plots. If NULL a default is chosen.

par.list

Argument list to par() in case pkg="graphics".

vp1d,vp2d,vp

The viewport()s passed to plot1d, plot2d and the overall frame grob (containing the whole zen plot), respectively.

...

Additional arguments passed to both plot1d() and plot2d().

Value

unfold() returns a list consisting of the path (itself a list containing turns (a character vector with elements in “l”, “r”, “d”, “u”), positions (a matrix of indices in the occupancy matrix) and the occupancy matrix itself (a matrix with elements in 0–4 where 0 stands for “not occupied” and 1–4 encode “l”, “r”, “d”, “u”)) and details about the layout (another list).

invisible unless assigned to a variale in which case a list containing the path and layout (and the frame grob if pkg="grid") is returned.

Author(s)

Marius Hofert and Wayne Oldford

See Also

All provided functions (of the form *_1d_grid() or *_2d_grid()) as arguments to plot1d or plot2d; see plots_grid or plots_graphics. scale01() for scaling the data.

Examples

  1
  2
  3
  4
  5
  6
  7
  8
  9
 10
 11
 12
 13
 14
 15
 16
 17
 18
 19
 20
 21
 22
 23
 24
 25
 26
 27
 28
 29
 30
 31
 32
 33
 34
 35
 36
 37
 38
 39
 40
 41
 42
 43
 44
 45
 46
 47
 48
 49
 50
 51
 52
 53
 54
 55
 56
 57
 58
 59
 60
 61
 62
 63
 64
 65
 66
 67
 68
 69
 70
 71
 72
 73
 74
 75
 76
 77
 78
 79
 80
 81
 82
 83
 84
 85
 86
 87
 88
 89
 90
 91
 92
 93
 94
 95
 96
 97
 98
 99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
require(zenplots)


### How the zen layout works ###################################################

## Auxiliary function
correctly_fails <- function(x)
    is(tryCatch(x, error=function(e) e), "simpleError")

## Generate data
n <- 1000 # sample size
d <- 20 # dimension
set.seed(271) # set seed (for reproducibility)
x <- matrix(rnorm(n*d), ncol=d) # i.i.d. N(0,1) data

## Call zenplot() in various cases
## Zero 2d plots (1st plot on the path)
stopifnot(correctly_fails(zenplot(x[,1], n2dcol=0)))
zenplot(x[,1], n2dcol=1) # 1d
zenplot(x[,1], n2dcol=1, pkg="grid") # 1d; with grid

## One 2d plot (2nd/3rd plot on the path)
zenplot(x[,1:2], n2dcol=1, last1d=FALSE) # 1d, 2d
zenplot(x[,1:2], n2dcol=1) # 1d, 2d, 1d
zenplot(x[,1:2], n2dcol=1, last1d=FALSE, pkg="grid") # 1d, 2d; with grid
zenplot(x[,1:2], n2dcol=1, pkg="grid") # 1d, 2d, 1d; with grid

## Two 2d plots (4th/5th plot on the path)
zenplot(x[,1:3], n2dcol=2, last1d=FALSE) # 1d, 2d, 1d, 2d
stopifnot(correctly_fails(zenplot(x[,1:3], n2dcol=1))) # 1d, 2d, 1d, 2d, 1d
stopifnot(correctly_fails(zenplot(x[,1:3], n2dcol=1, method="double.zigzag"))) # 1d, 2d, 1d, 2d, 1d
stopifnot(correctly_fails(zenplot(x[,1:3], n2dcol=1, method="single.zigzag"))) # 1d, 2d, 1d, 2d, 1d
zenplot(x[,1:3], n2dcol=2) # 1d, 2d, 1d, 2d, 1d
zenplot(x[,1:3], n2dcol=2, method="double.zigzag") # 1d, 2d, 1d, 2d, 1d
zenplot(x[,1:3], n2dcol=2, method="single.zigzag") # 1d, 2d, 1d, 2d, 1d

## Three 2d plots (6th/7th plot on the path)
zenplot(x[,1:4], n2dcol=2, last1d=FALSE) # 1d, 2d, 1d, 2d, 1d, 2d
zenplot(x[,1:4], n2dcol=2) # 1d, 2d, 1d, 2d, 1d, 2d, 1d
zenplot(x[,1:4], n2dcol=2, method="double.zigzag") # 1d, 2d, 1d, 2d, 1d, 2d, 1d
zenplot(x[,1:4], n2dcol=2, method="single.zigzag") # 1d, 2d, 1d, 2d, 1d, 2d, 1d

## Four 2d plots (8th/9th plot on the path)
zenplot(x[,1:5], n2dcol=2, last1d=FALSE) # 1d, 2d, 1d, 2d, 1d, 2d, 1d, 2d
zenplot(x[,1:5], n2dcol=2) # 1d, 2d, 1d, 2d, 1d, 2d, 1d, 2d, 1d
zenplot(x[,1:5], n2dcol=3) # 1d, 2d, 1d, 2d, 1d, 2d, 1d, 2d, 1d
zenplot(x[,1:5], n2dcol=3, method="double.zigzag") # 1d, 2d, 1d, 2d, 1d, 2d, 1d, 2d, 1d
zenplot(x[,1:5], n2dcol=3, method="single.zigzag") # 1d, 2d, 1d, 2d, 1d, 2d, 1d, 2d, 1d

## Large sub-data sets
zenplot(x[,1:18], n2dcol=5)
zenplot(x[,1:18], n2dcol=5, method="double.zigzag")
zenplot(x[,1:18], n2dcol=5, method="single.zigzag")
zenplot(x[,1:19], n2dcol=5)

## The full data with different n2dcol
zenplot(x, n2dcol=4)
zenplot(x, n2dcol=5)
zenplot(x, n2dcol=6)
zenplot(x, n2dcol=7)
zenplot(x, n2dcol=7, pkg="grid") # with grid
zenplot(x, n2dcol=8)
zenplot(x, n2dcol=9)
zenplot(x, n2dcol=10)
zenplot(x, n2dcol=11)
zenplot(x, n2dcol=12)


### Providing your own turns ###################################################

turns <- c("l","d","d","r","r","d","d","r","r","u","u","r","r","u","u","l","l",
           "u","u","l","l","u","u","l","l","d","d", "l","l","d","d","l","l","d",
           "d","r","r","d","d")
zenplot(x, turns=turns)
zenplot(x, turns=turns, pkg="grid") # with grid


### Providing your own plot1d() or plot2d() ####################################

## Examples with predefined plot1d() or plot2d()
zenplot(x, plot1d="label", plot2d="rect")
zenplot(x, plot1d="label", plot2d="rect", pkg="grid")
zenplot(x, plot1d="arrow", plot2d="rect")
zenplot(x, plot1d="arrow", plot2d="rect", pkg="grid")
zenplot(x, plot1d="arrow", plot2d="arrow")
zenplot(x, plot1d="arrow", plot2d="arrow", pkg="grid")
zenplot(x, plot1d=NULL) # omitting the 1d plots
zenplot(x, plot1d=NULL, pkg="grid")
zenplot(x, plot2d=NULL) # omitting the 2d plots
zenplot(x, plot2d=NULL, pkg="grid")

## Iterate over all predefined plot1d()
methods <- eval(formals(zenplot)$plot1d)
for(p1d in methods) {
    zenplot(x, plot1d=p1d) # with graphics
    zenplot(x, plot1d=p1d, pkg="grid") # with grid
}

## 2-sided densities
zenplot(x, plot1d=function(...) density_1d_graphics(..., method="double"))
zenplot(x, plot1d=function(...)
        density_1d_grid(..., method="double"), pkg="grid")

## Colorized rugs as plot1d()
basecol <- c("royalblue3", "darkorange2", "maroon3")
palette <- colorRampPalette(basecol, space="Lab")
cols <- palette(d) # different color for each 1d plot
zenplot(x, plot1d=function(plotID, ...)
        rug_1d_graphics(col=cols[plotID$plotNo], ...))
require(grid) # for gTree() and gList()
zenplot(x, pkg="grid", # you are responsible for choosing the right pkg (cannot be tested!)
        plot1d=function(plotID, ...)
               rug_1d_grid(col=cols[plotID$plotNo], ...))

## Rectangles with labels as plot2d() (shows how to overlay plots)
## With graphics
zenplot(x, plot1d="arrow", plot2d=function(...){
            rect_2d_graphics(...); label_2d_graphics(..., add=TRUE)})
## With grid
zenplot(x, pkg="grid", plot1d="arrow", plot2d=function(x, plotID, ...)
    gTree(children=gList(rect_2d_grid(...),
                         label_2d_grid(x=x, plotID=plotID, ...))))

## Rectangles with labels outside the 2d plotting region as plot2d()
## With graphics
zenplot(x, plot1d="arrow", plot2d=function(...){
            rect_2d_graphics(...)
            label_2d_graphics(..., add=TRUE, xpd=NA, srt=90,
                              loc.x=1.08, loc.y=-0.04, adj=c(0,1), cex=0.56)})
## With grid
zenplot(x, pkg="grid", plot1d="arrow", plot2d=function(x, plotID, ...)
    gTree(children=gList(rect_2d_grid(...),
                         label_2d_grid(..., x=x, plotID=plotID,
                                       loc.x=1.03, loc.y=0,
                                       just=c("left", "top"),
                                       rot=90, cex=0.37))))
## Note: The above four plots show the variable names if x has column names

## An example showing how to modify graphical parameters of plot1d(), plot2d()
## With graphics
zenplot(x,
        plot1d=function(...) {
            lines_1d_graphics(col=basecol[1], lwd=1.4, ...)},
        plot2d=function(...) {
            rect_2d_graphics(..., border="grey50", lty=3)
            arrow_2d_graphics(..., add=TRUE)
            label_2d_graphics(..., col=basecol[3], add=TRUE)
})

## With grid
zenplot(x, pkg="grid",
        plot1d=function(horizontal, draw=FALSE, ...)
            lines_1d_grid(horizontal=horizontal,
                          col=basecol[1], lwd=1.4, draw=draw),
        plot2d=function(x, plotID, draw=FALSE, ...)
            gTree(children=gList(rect_2d_grid(...,
                                              col="grey50", lty=3, draw=draw),
                                 arrow_2d_grid(..., draw=draw),
                                 label_2d_grid(x=x, plotID=plotID,
                                               col=basecol[3], draw=draw))))

## A more sophisticated example

## 1) Build a random sample from a 17-dimensional grouped t copula
d. <- c(8, 5, 4) # sector dimensions
nu <- c(rep(10,d.[1]), rep(3,d.[2]), rep(0.5,d.[3])) # d.o.f. for each dimension
d <- length(nu) # total dimension
n <- 500 # sample size
set.seed(271)
Z <- matrix(rnorm(n*d), ncol=n) # (d,n)-matrix
Sigma <- matrix(0.5, nrow=d, ncol=d)
diag(Sigma) <- 1
L <- t(chol(Sigma)) # L: LL^T = Sigma
Y <- t(L %*% Z) # (n,d)-matrix containing n d-vectors following N(0,Sigma)
U. <- runif(n)
W <- sapply(nu, function(nu.) 1/qgamma(U., shape=nu./2, rate=nu./2)) # (n,d)-matrix
X <- sqrt(W) * Y # (n,d)-matrix
U <- sapply(1:d, function(j) pt(X[,j], df=nu[j])) # (n,d)-matrix

## 2) Plot the data with a pairs plot, colorizing the groups
colmat <- matrix("black", nrow=d, ncol=d)
colmat[1:d.[1], 1:d.[1]] <- basecol[1]
colmat[(d.[1]+1):(d.[1]+d.[2]), (d.[1]+1):(d.[1]+d.[2])] <- basecol[2]
colmat[(d.[1]+d.[2]+1):d, (d.[1]+d.[2]+1):d] <- basecol[3]
diag(colmat) <- NA # remove colors corresponding to diagonal entries (no plotting)
cols <- as.vector(colmat) # convert to a vector
cols <- cols[!is.na(cols)] # remove NA entries corresponding to diagonal
## Define panel function for colorizing the groups
count <- 0
mypanel <- function(x, y, ...) # panel function for colorizing groups
    { count <<- count+1; points(x, y, pch=".", col=cols[count]) }
## Plot
pairs(U, panel=mypanel, gap=0,
      labels=as.expression( sapply(1:d, function(j) bquote(italic(U[.(j)]))) ))

## 3) Zen plot of a random path through all pairs, colorizing the respective group
## Define our own points_2d_grid() for colorizing the groups
my_points_2d_grid <- function(x, plotID, draw=TRUE, ...) {
    var <- as.numeric(plotID$name) # pick out the names (variable numbers)
    col <- if(all(1 <= var & var <= d.[1])) { basecol[1] } else {
            if(all(d.[1]+1 <= var & var <= d.[1]+d.[2])) { basecol[2] } else {
               if(all(d.[1]+d.[2]+1 <= var & var <= d)) basecol[3] else "black"
            }
        }
    grid.points(x=x[,1], y=x[,2], pch=21, size=unit(0.02, "npc"),
                gp=gpar(col=col, ...), draw=draw)
}
## Plot a random permutation of columns via a zen plot
## Note: We set column labels here, as otherwise the labels can only
##       show *indices* of the variables to be plotted, i.e., the column
##       number in U[,ord], not the original column number in U (which
##       is what we want to see in order to see how our 'path' through
##       the pairs of variables looks like.
colnames(U) <- 1:d
set.seed(1)
(ord <- sample(1:d, size=d)) # path; 1:d would walk parallel to the secondary diagonal
zenplot(U[,ord], pkg="grid",
        plot1d=function(..., draw) arrow_1d_grid(...,
                        col="grey50", draw=FALSE),
        plot2d=function(x, plotID, draw=FALSE, ...)
            gTree(children=gList(
                  my_points_2d_grid(x=x, plotID, alpha=0.6, draw=draw),
                  rect_2d_grid(col="grey50", lty=3, draw=draw),
                  label_2d_grid(x=x, plotID=plotID, loc.x=1.02, loc.y=0,
                                just=c("left", "top"), rot=90, cex=0.4,
                                fontface="bold", draw=draw) )))
## => The points are colorized correctly (compare with the pairs plot)

zenplots documentation built on May 2, 2019, 4:34 p.m.

Related to zenplot in zenplots...