We have a spherical globe of radius 1, centre 1,1. There is spot randomly located on the globes surface. We are generating independent Unif(-1,1) random variables X,Y,Z which will be the coordinates of the random point. Divide (X,Y,Z) by √{X2 +Y2 +Z2} to get a point 1m from the centre of the globe. **
Write a function sample3d that produces a sample of random vectors (X, Y, Z), each of which is a point from a uniform distribution on the globe’s surface. Calling this function by the command sample3d(n) should produce an n × 3 array, where each row is a vector (X, Y, Z).
I have managed it up to ** but cannot create the sample3d, any help would be appreciated!
I had fun trying to come up with something helpful, here is what I got:
First, I defined a function norm.2
which calculates the two norm of a vector:
norm.2 <- function(x, na.rm){
if(length(dim(x)) != 0){
v1.logical <- ifelse(missing(na.rm), FALSE, TRUE)
return(sqrt(colSums(x^2, na.rm = v1.logical)))
}
if(length(dim(x)) == 0){
v1.logical <- ifelse(missing(na.rm), FALSE, TRUE)
return(sqrt(sum(x^2, na.rm = v1.logical)))
}
}
Then, I proceeded to define a function sample3d
which will give n points in the 3-dimensional space, all of which with norm 1, i.e. on the 2-sphere:
sample3d <- function(n, Boundary){
M <- ifelse(missing(Boundary), sqrt(2e+300), Boundary)
x1 <- runif(n, min = -M, max = M)
x2 <- runif(n, min = -M, max = M)
x3 <- runif(n, min = -M, max = M)
x <- t(cbind(x1,x2,x3))
p <- t(t(x)/norm.2(x))
df <- data.frame(t(p), stringsAsFactors = FALSE)
return(df)
}
Here is a sample of the result:
> head(sample3d(10000))
x1 x2 x3
1 0.321159709 -0.5014622 -0.8033630
2 0.488181408 0.5547003 -0.6737852
3 -0.661576495 -0.4592729 0.5927773
4 -0.333447393 0.9331249 -0.1345016
5 -0.009070263 0.4267690 0.9043152
6 -0.375122328 -0.2393661 -0.8955373
Now, using the plotly
package, we can have some fun visualizing it:
library(plotly)
dat <- sample3d(100000)
p <- plot_ly(dat, x = ~x1, y = ~x2, z = ~x3, color = norm.2(t(dat)), colors = c('#BF382A', '#0C4B8E')) %>%
add_markers() %>%
layout(scene = list(xaxis = list(title = 'X'),
yaxis = list(title = 'Y'),
zaxis = list(title = 'Z')))