web-dev-qa-db-fra.com

Tracer deux graphes dans le même tracé en R

Je voudrais tracer y1 et y2 dans le même complot.

x  <- seq(-2, 2, 0.05)
y1 <- pnorm(x)
y2 <- pnorm(x, 1, 1)
plot(x, y1, type = "l", col = "red")
plot(x, y2, type = "l", col = "green")

Mais quand je le fais comme ça, ils ne sont pas complotés ensemble dans le même complot.

Dans Matlab, on peut faire hold on, mais est-ce que quelqu'un sait comment faire cela en R?

517

lines() ou points() s'ajoute au graphique existant, mais ne crée pas de nouvelle fenêtre. Donc tu devrais faire

plot(x,y1,type="l",col="red")
lines(x,y2,col="green")
560
bnaul

Vous pouvez également utiliser par et tracer sur le même graphique mais sur un axe différent. Quelque chose comme suit:

plot( x, y1, type="l", col="red" )
par(new=TRUE)
plot( x, y2, type="l", col="green" )

Si vous lisez en détail à propos de par dans R, vous pourrez générer des graphiques vraiment intéressants. Un autre livre à regarder est R Graphics de Paul Murrel.

200
Sam

Lors de la construction de tracés multicouches, il convient de considérer le package ggplot. L'idée est de créer un objet graphique avec une esthétique de base et de l'améliorer progressivement.

Le style ggplot nécessite que les données soient emballées dans data.frame.

# Data generation
x  <- seq(-2, 2, 0.05)
y1 <- pnorm(x)
y2 <- pnorm(x,1,1)
df <- data.frame(x,y1,y2)

Solution basique:

require(ggplot2)

ggplot(df, aes(x)) +                    # basic graphical object
  geom_line(aes(y=y1), colour="red") +  # first layer
  geom_line(aes(y=y2), colour="green")  # second layer

Ici, + operator est utilisé pour ajouter des couches supplémentaires à un objet de base.

Avec ggplot, vous avez accès à un objet graphique à chaque étape du traçage. Disons, la configuration pas à pas habituelle peut ressembler à ceci:

g <- ggplot(df, aes(x))
g <- g + geom_line(aes(y=y1), colour="red")
g <- g + geom_line(aes(y=y2), colour="green")
g

g produit le tracé et vous pouvez le voir à chaque étape (ainsi, après la création d'au moins un calque). D'autres enchantements de la parcelle sont également réalisés avec un objet créé. Par exemple, nous pouvons ajouter des étiquettes pour axises:

g <- g + ylab("Y") + xlab("X")
g

Final g ressemble à:

enter image description here

UPDATE (2013-11-08):

Comme indiqué dans les commentaires, la philosophie de ggplot suggère d'utiliser des données au format long. Vous pouvez vous référer à cette réponse https://stackoverflow.com/a/19039094/1796914 pour voir le code correspondant.

107
redmode

Je pense que la réponse que vous recherchez est la suivante:

plot(first thing to plot)
plot(second thing to plot,add=TRUE)
37
user3749764

Utilisez la fonction matplot:

matplot(x, cbind(y1,y2),type="l",col=c("red","green"),lty=c(1,1))

utilisez ceci si y1 et y2 sont évalués aux mêmes points x. Il ajuste l’axe Y en fonction de ce qui est le plus grand (y1 ou y2), contrairement à certaines des autres réponses ici qui coupent y2 s’il devient plus grand que y1 (Les solutions de ggplot sont généralement acceptables).

Sinon, et si les deux lignes n'ont pas les mêmes coordonnées x, définissez les limites de l'axe sur le premier tracé et ajoutez:

x1  <- seq(-2, 2, 0.05)
x2  <- seq(-3, 3, 0.05)
y1 <- pnorm(x1)
y2 <- pnorm(x2,1,1)

plot(x1,y1,ylim=range(c(y1,y2)),xlim=range(c(x1,x2)), type="l",col="red")
lines(x2,y2,col="green")

Je suis étonné que ce Q ait 4 ans et que personne n'ait mentionné matplot ou x/ylim...

25
Spacedman

tl; dr: Vous voulez utiliser curve (avec add=TRUE) ou lines.


Je ne suis pas d'accord avec par(new=TRUE) parce que cela double l'impression des graduations et des libellés d'axe. Par exemple

sine and parabola

La sortie de plot(sin); par(new=T); plot( function(x) x**2 ).

Regardez comme les étiquettes d'axe vertical sont foirées! Puisque les plages sont différentes, vous devez définir ylim=c(lowest point between the two functions, highest point between the two functions), ce qui est moins facile que ce que je vais vous montrer --- et manière moins facile si vous vouloir ajouter non pas deux courbes, mais plusieurs.


Ce qui m'a toujours dérouté dans le tracé est la différence entre curve et lines. (Si vous ne vous rappelez pas que ce sont les noms des deux commandes de traçage importantes, il suffit de chanter le.)

Voici la grande différence entre curve et lines.

curve trace une fonction, comme curve(sin). lines trace les points avec les valeurs x et y, tels que: lines( x=0:10, y=sin(0:10) ).

Et voici une différence mineure: curve doit être appelé avec add=TRUE pour ce que vous essayez de faire, alors que lines suppose déjà que vous ajoutez à un tracé existant.

id & sine

Voici le résultat de l'appel de plot(0:2); curve(sin).


Dans les coulisses, consultez methods(plot). Et vérifiez body( plot.function )[[5]]. Lorsque vous appelez plot(sin) R découvre que sin est une fonction (et non des valeurs y) et utilise la méthode plot.function, qui appelle finalement curve. Donc, curve est l’outil destiné à gérer les fonctions.

24
isomorphismes

Comme décrit par @redmode, vous pouvez tracer les deux lignes dans le même périphérique graphique à l'aide de ggplot. Dans cette réponse, les données étaient dans un format "large". Cependant, lorsque vous utilisez ggplot, il est généralement plus pratique de conserver les données dans un bloc de données dans un format "long". Ensuite, en utilisant différentes "variables de regroupement" dans les arguments aesthetics, les propriétés de la ligne, telles que le type de ligne ou la couleur, varieront en fonction de la variable de regroupement et les légendes correspondantes apparaîtront.

Dans ce cas, nous pouvons utiliser l’asthétique colour, qui fait correspondre la couleur des lignes à différents niveaux d’une variable de l’ensemble de données (ici: y1 vs y2). Mais nous devons d’abord faire fondre les données d’un format large à un format long, en utilisant par exemple la fonction 'fondre' du paquetage reshape2. D'autres méthodes pour remodeler les données sont décrites ici: Remodelage du fichier data.frame du format large au format long .

library(ggplot2)
library(reshape2)

# original data in a 'wide' format
x  <- seq(-2, 2, 0.05)
y1 <- pnorm(x)
y2 <- pnorm(x, 1, 1)
df <- data.frame(x, y1, y2)

# melt the data to a long format
df2 <- melt(data = df, id.vars = "x")

# plot, using the aesthetics argument 'colour'
ggplot(data = df2, aes(x = x, y = value, colour = variable)) + geom_line()

enter image description here

16
Henrik

Si vous utilisez des graphiques de base (c'est-à-dire pas des graphiques en grille/grille), vous pouvez imiter la fonction de maintien de MATLAB en utilisant les fonctions points/lignes/polygones pour ajouter des détails supplémentaires à vos tracés sans créer de nouveau tracé. Dans le cas d'une mise en page multiplot, vous pouvez utiliser par(mfg=...) pour choisir le tracé auquel vous ajoutez des éléments.

15
mcabral

si vous voulez diviser l'écran, vous pouvez le faire comme ceci:

(par exemple pour 2 parcelles côte à côte)

par(mfrow=c(1,2))

plot(x)

plot(y) 

lien de référence

14
Hamed2005

Vous pouvez utiliser des points pour le superplot, c'est-à-dire.

plot(x1, y1,col='red')

points(x2,y2,col='blue')
12
brainstorm

Plutôt que de conserver les valeurs à tracer dans un tableau, stockez-les dans une matrice. Par défaut, toute la matrice sera traitée comme un seul jeu de données. Toutefois, si vous ajoutez le même nombre de modificateurs au tracé, par exemple, col (), comme vous avez des lignes dans la matrice, R déterminera que chaque ligne doit être traitée indépendamment. Par exemple:

x = matrix( c(21,50,80,41), nrow=2 )
y = matrix( c(1,2,1,2), nrow=2 )
plot(x, y, col("red","blue")

Cela devrait fonctionner à moins que vos ensembles de données ne soient de tailles différentes.

7
cranberry

Matlab idiomatique plot(x1,y1,x2,y2) peut être traduit en R avec ggplot2 par exemple de cette manière:

x1 <- seq(1,10,.2)
df1 <- data.frame(x=x1,y=log(x1),type="Log")
x2 <- seq(1,10)
df2 <- data.frame(x=x2,y=cumsum(1/x2),type="Harmonic")

df <- rbind(df1,df2)

library(ggplot2)
ggplot(df)+geom_line(aes(x,y,colour=type))

enter image description here

Inspiré de Tingting Zhao's Tracés à deux lignes avec différentes étendues d'axe x à l'aide de ggplot2 .

5
Alessandro Jacopson

Vous pouvez utiliser la fonction ggplotly() du package plotly pour transformer l'un des éléments gggplot2 exemples ici dans un complot interactif, mais je pense que ce genre de complot est mieux sans ggplot2 :

# call Plotly and enter username and key
library(plotly)
x  <- seq(-2, 2, 0.05)
y1 <- pnorm(x)
y2 <- pnorm(x, 1, 1)

plot_ly(x = x) %>%
  add_lines(y = y1, color = I("red"), name = "Red") %>%
  add_lines(y = y2, color = I("green"), name = "Green")

enter image description here

4
Mateo Sanchez

Vous pouvez également créer votre tracé en utilisant ggvis :

library(ggvis)

x  <- seq(-2, 2, 0.05)
y1 <- pnorm(x)
y2 <- pnorm(x,1,1)
df <- data.frame(x, y1, y2)

df %>%
  ggvis(~x, ~y1, stroke := 'red') %>%
  layer_paths() %>%
  layer_paths(data = df, x = ~x, y = ~y2, stroke := 'blue')

Cela créera l'intrigue suivante:

enter image description here

4
epo3

on peut aussi utiliser la librairie de treillis

library(lattice)
x <- seq(-2,2,0.05)
y1 <- pnorm(x)
y2 <- pnorm(x,1,1)
xyplot(y1 + y2 ~ x, ylab = "y1 and y2", type = "l", auto.key = list(points = FALSE,lines = TRUE))

Pour des couleurs spécifiques

xyplot(y1 + y2 ~ x,ylab = "y1 and y2", type = "l", auto.key = list(points = F,lines = T), par.settings = list(superpose.line = list(col = c("red","green"))))

enter image description here

1
Varn K

Utilisation de plotly (ajout de la solution de plotly avec les axes y principal et secondaire - il semble manquer):

library(plotly)     
x  <- seq(-2, 2, 0.05)
y1 <- pnorm(x)
y2 <- pnorm(x, 1, 1)

df=cbind.data.frame(x,y1,y2)

  plot_ly(df) %>%
    add_trace(x=~x,y=~y1,name = 'Line 1',type = 'scatter',mode = 'lines+markers',connectgaps = TRUE) %>%
    add_trace(x=~x,y=~y2,name = 'Line 2',type = 'scatter',mode = 'lines+markers',connectgaps = TRUE,yaxis = "y2") %>%
    layout(title = 'Title',
       xaxis = list(title = "X-axis title"),
       yaxis2 = list(side = 'right', overlaying = "y", title = 'secondary y axis', showgrid = FALSE, zeroline = FALSE))

Capture d'écran de la démo de travail:

enter image description here

1
Saurabh Chauhan