J'ai donc ce code qui produit la surface exacte

f = function(x, y){
    z = ((x^2)+(3*y^2))*exp(-(x^2)-(y^2))
}
plot3d(f, col = colorRampPalette(c("blue", "white")), 
       xlab = "X", ylab = "Y", zlab = "Z", 
       xlim = c(-3, 3), ylim = c(-3, 3),
       aspect = c(1, 1, 0.5))

Donnant l'intrigue suivante: 3D exact plot Maintenant, j'ai un code qui fait un algorithme de métropole à marche aléatoire pour reproduire l'image ci-dessus. Je pense que cela fonctionne comme si je fais un autre tracé de ces valeurs calculées, j'obtiens l'image suivante avec 500 points. Voici le code

open3d()
plot3d(x0, y0, f(x0, y0), type = "p")

Ce qui donne l'intrigue suivante: entrez la description de l'image ici Je sais qu'il est difficile de regarder cette image fixe, mais pouvoir faire pivoter l'échantillonnage fonctionne.

Voici maintenant ma question: comment puis-je utiliser plot3d() pour avoir une surface qui relie tous ces points et donne une représentation plus irrégulière du tracé exact? Ou comment puis-je avoir chaque point de l'axe z comme une barre du plan xy? Je veux juste quelque chose de plus tridimensionnel que des points et je ne trouve pas comment faire cela.

Merci de votre aide

r rgl
1
MRT 20 nov. 2018 à 20:10

3 réponses

Meilleure réponse

Vous pouvez le faire en triangulant la surface. Vous ne nous communiquez pas vos données réelles, mais je peux créer des données similaires en utilisant

f = function(x, y){
    z = ((x^2)+(3*y^2))*exp(-(x^2)-(y^2))
}
x <- runif(500, -3, 3)
y <- runif(500, -3, 3)
z <- f(x, y)

Ensuite, le tracé est fait en utilisant la méthode dans ?persp3d.deldir:

library(deldir)
library(rgl)
col <- colorRampPalette(c("blue", "white"))(20)[1 + round(19*(z - min(z))/diff(range(z)))]
dxyz <- deldir::deldir(x, y, z = z, suppressMsge = TRUE)
persp3d(dxyz, col = col, front = "lines", back = "lines")

Cela peut nécessiter des correctifs cosmétiques, par exemple

aspect3d(2, 2, 1)

Après quelques rotations, cela me donne l'intrigue suivante:

enter image description here

2
user2554330 26 nov. 2018 à 16:34

Voici un graphique avec seulement 50 points en utilisant mon code d'origine.

Scatter graph of 50 points

Quand j'applique ensuite ce qui a été dit par Stéphane Laurent, j'obtiens alors cette intrigue qui semble trop précise compte tenu des points réels que j'ai

wire plot

Vous devez peut-être m'expliquer ce qui se passe réellement dans la fonction parametric3d

0
MRT 25 nov. 2018 à 16:51

Je ne suis pas sûr de comprendre ce que vous voulez. Si je comprends bien, voici une solution. Définissez une représentation paramétrique de votre surface:

fx <- function(u,v) u
fy <- function(u,v) v
fz <- function(u,v){
  ((u^2)+(3*v^2))*exp(-(u^2)-(v^2))
}

Disons que vous avez ces points:

x0 <- seq(-3, 3, length.out = 20)
y0 <- seq(-3, 3, length.out = 20)

Ensuite, vous pouvez utiliser la fonction parametric3d du package misc3d, avec l'option fill=FALSE pour obtenir un wireframe:

library(misc3d)
parametric3d(fx, fy, fz, u=x0, v=y0, 
             color="blue", fill = FALSE)

enter image description here

C'est ce que tu veux?

Pour obtenir des barres verticales, utilisez la fonction segments3d de rgl:

i <- 8
bar <- rbind(c(x0[i],y0[i],0),c(x0[i],y0[i],f(x0[i],y0[i])))
segments3d(bar, color="red")
0
Stéphane Laurent 21 nov. 2018 à 15:58