Error: Mapping must be created by 'aes()' - r

I am using a for loop to create 100 ggplots in R to be graphed onto one sheet of paper. However, I keep getting a mapping must be created by aes() error and I am not sure how to fix it.
I have tried the get function with and without environments, unclear where to go next.
for(i in 1:99){
nam <- paste("p", i, sep = "")
otunam <- paste("OTU", i, sep = "")
otunam1 <- get(otunam, envir = as.environment(histotu), inherits = TRUE)
plot <- ggplot(histotu, aes(x=otunam)) + geom_histogram(histotu, stat = "bin", binwidth = 0.01) + geom_vline(xintercept=expD[1,i], color = "red") + xlab(otunam)
assign(nam, plot)
}
I would like to clear this error and be able to make 100 graphs using grid.arrange. I have this part to work, but not the for loop to create the objects that it calls.

Related

I can't get my plots to a single grid please help correct my code

I have 11 plots and used a looping function to plot them see my code below. However, I can't get them to fit in just 1 page or less. The plots are actually too big. I am using R software and writing my work in RMarkdown. I have spent almost an entire week trying to resolve this.
group_by(Firm_category) %>%
doo(
~ggboxplot(
data =., x = "Means.type", y = "means",
fill ="grey", palette = "npg", legend = "none",
ggtheme = theme_pubr()
),
result = "plots"
)
graph3
# Add statistical tests to each corresponding plot
Firm_category <- graph3$Firm_category
xx <- for(i in 1:length(Firm_category)){
graph3.i <- graph3$plots[[i]] +
labs(title = Firm_category[i]) +
stat_pvalue_manual(stat.test[i, ], label = "p.adj.signif")
print(graph3.i)
}
#output3.long data sample below as comments
#Firm_category billmonth Means.type means
#Agric 1 Before 38.4444
#Agric 1 After 51.9
Complete data is on my github: https://github.com/Fridahnyakundi/Descriptives-in-R/blob/master/Output3.csv
This code prints all the graphs but in like 4 pages. I want to group them into a grid. I have tried to add all these codes below just before my last curly bracket and none is working, please help me out.
library(cowplot)
print(plot_grid(plotlist = graph3.i[1:11], nrow = 4, ncol = 3))
library(ggpubr)
print(ggarrange(graph3.i[1:11], nrow = 4, ncol = 3))
I tried the gridExtra command as well (they all seem to do the same thing). I am the one with a mistake and I guess it has to do with my list. I read a lot of similar work here, some suggested
dev.new()
dev.off()
I still didn't get what they do. But adding either of them caused my code to stop.
I tried defining my 'for' loop function say call it 'XX', then later call it to make a list of graph but it returned NULL output.
I have tried defining an empty list (as I read in some answers here) then counting them to make a list that can be printed but I got so many errors.
I have done this for almost 3 days and will appreciate your help in resolving this.
Thanks!
I tried to complete your code ... and this works (but I don't have your 'stat.test' object). Basically, I added a graph3.i <- list() and replaced graph3.i in the loop ..
Is it what you wanted to do ?
library(magrittr)
library(dplyr)
library(rstatix)
library(ggplot2)
library(ggpubr)
data <- read.csv(url('http://raw.githubusercontent.com/Fridahnyakundi/Descriptives-in-R/master/Output3.csv'))
graph3 <- data %>% group_by(Firm_category) %>%
doo(
~ggboxplot(
data =., x = "Means.type", y = "means",
fill ="grey", palette = "npg", legend = "none",
ggtheme = theme_pubr()
),
result = "plots"
)
graph3
# Add statistical tests to each corresponding plot
graph3.i <- list()
Firm_category <- graph3$Firm_category
xx <- for(i in 1:length(Firm_category)){
graph3.i[[i]] <- graph3$plots[[i]] +
labs(title = Firm_category[i]) # +
# stat_pvalue_manual(stat.test[i, ], label = "p.adj.signif")
print(graph3.i)
}
library(cowplot)
print(plot_grid(plotlist = graph3.i[1:11], nrow = 4, ncol = 3))

Weird characters appearing in the plot legend when using DoHeatmap

I was using Seurat to analyse single cell RNA-seq data and I managed to draw a heatmap plot with DoHeatmap() after clustering and marker selection, but got a bunch of random characters appearing in the legend. They are random characters as they will change every time you run the code. I was worrying over it's something related to my own dataset, so I then tried the test Seurat object 'ifnb' but still got the same issue (see the red oval in the example plot).
example plot
I also tried importing the Seurat object in R in the terminal (via readRDS) and ran the plotting function, but got the same issue there, so it's not a Rstudio thing.
Here are the codes I ran:
'''
library(Seurat)
library(SeuratData)
library(patchwork)
InstallData("ifnb")
LoadData("ifnb")
ifnb.list <- SplitObject(ifnb, split.by = "stim")
ifnb.list <- lapply(X = ifnb.list, FUN = function(x) {
x <- NormalizeData(x)
x <- FindVariableFeatures(x, selection.method = "vst", nfeatures = 2000)
})
features <- SelectIntegrationFeatures(object.list = ifnb.list)
immune.anchors <- FindIntegrationAnchors(object.list = ifnb.list, anchor.features = features)
immune.combined <- IntegrateData(anchorset = immune.anchors)
immune.combined <- ScaleData(immune.combined, verbose = FALSE)
immune.combined <- RunPCA(immune.combined, npcs = 30, verbose = FALSE)
immune.combined <- RunUMAP(immune.combined, reduction = "pca", dims = 1:30)
immune.combined <- FindNeighbors(immune.combined, reduction = "pca", dims = 1:30)
immune.combined <- FindClusters(immune.combined, resolution = 0.5)
DefaultAssay(immune.combined) <- 'RNA'
immune_markers <- FindAllMarkers(immune.combined, latent.vars = "stim", test.use = "MAST", assay = 'RNA')
immune_markers %>%
group_by(cluster) %>%
top_n(n = 10, wt = avg_log2FC) -> top10_immune
DoHeatmap(immune.combined, slot = 'data',features = top10_immune$gene, group.by = 'stim', assay = 'RNA')
'''
Does anyone have any idea how to solve this issue other than reinstalling everything?
I have been having the same issue myself and while I have solved it by not needing the legend, I think you could use this approach and use a similar solution:
DoHeatmap(immune.combined, slot = 'data',features = top10_immune$gene, group.by = 'stim', assay = 'RNA') +
scale_color_manual(
values = my_colors,
limits = c('CTRL', 'STIM'))
Let me know if this works! It doesn't solve the source of the odd text values but it does the job! If you haven't already, I would recommend creating a forum question on the Seurat forums to see where these characters are coming from!
When I use seurat4.0, I met the same problem.
While I loaded 4.1, it disappeared

Plotting a tree - collapsing a vector of nodes

I am trying to plot a large tree using ggtree, but, due to its size, I would like to collapse multiple nodes. I am following a tutorial , but it collapses the nodes one at the time, and this is not an option in my case.
Here is my code:
library(ggtree)
library(ape)
library(ggplot2)
library(colorspace)
library(Biostrings)
library(phytools)
library(treeio)
library(dplyr)
library(readr)
library(tidyr)
library(reshape2)
tempnwk<- "((('clade01_1':1.35E-4,('clade01_2':1.0E-6,'clade01_3':1.0E-6):3.3E-5):3.3E-5,('clade02_1':2.7E-4,'clade02_2':3.3E-5):3.3E-5):1.0E-6,'clade03_1':1.0E-6);"
testTree0 <- read.tree(text = tempnwk)
#
testcollapse0<- ggtree(testTree0)
#Now, this works:
#
testcollapse0b<- testcollapse0 %>% collapse(node = 10) +
geom_point2(aes(subset=(node==10)),
shape=21, size=5, fill='green')
testcollapse0b<- collapse(testcollapse0b, node = 11) +
geom_point2(aes(subset=(node==11)),
shape=21, size=5, fill='red')
testcollapse0b ####This works
#
#
##############THis does not:
nodes2go<- c(10, 11)
myTestCols<- c('green', 'red')
testcollapse1<- testcollapse0
for(i in 1:2) {
testcollapse1<- collapse(
testcollapse1, node = nodes2go[i]) +
geom_point2(
aes(subset=(node==i)), shape=23,
size=7, fill=myTestCols[i])
}
rm(i)
#
testcollapse1 + geom_text(aes(label=label))
#
#Error in FUN(X[[i]], ...) : object 'i' not found
I need some help, I am not sure how to fix it. I had a look at drop.tip, but I am not sure that is what I want, since I still want a colored dot where the collapsed node is.
I am looking forward to your feedback, thank you for your kind attention.
Well,
While waiting for a sane way to do it, quick and dirty will do the job:
myTestCols2<- c("'green'", "'red'")
testcollapse2<- testcollapse0
teststring0<- "testcollapse2<- collapse(testcollapse2, node=NODE) + geom_point2(aes(subset=(node==NODE)), shape=23, size=7, fill=COLOR);"
testString2<- character()
for(i in 1:2) {
indString<- gsub(
pattern = "NODE",replacement = nodes2go[i],
x = teststring0)
indString<- gsub(
pattern = "COLOR", replacement = myTestCols2[i],
x = indString)
testString2<- c(testString2, indString)
}
rm(i, indString)
#
#Run the command
eval(parse(text = testString2))
##And now plot:
testcollapse2
And yes, I am aware that there must be a better way to do it 🙄

R baseline package saving plots in a loop

I'm trying to optimize the parameters for baseline in the R baseline package by changing each parameters in a loop and comparing plots to determine which parameters give me the best baseline.
I currently have the code written so that the loop produces each plot, but I'm having trouble with getting the plot saved as the class of each object I'm creating is a baseline package-specific (which I'm suspecting is the problem here).
foo <- data.frame(Date=seq.Date(as.Date("1957-01-01"), by = "day",
length.out = ncol(milk$spectra)),
Visits=milk$spectra[1,],
Old_baseline_visits=milk$spectra[1,], row.names = NULL)
foo.t <- t(foo$Visits)
#the lines above were copied from https://stackoverflow.com/questions/37346967/r-packagebaseline-application-to-sample-dataset to make a reproducible dataset
df <- expand.grid(lambda=seq(1,10,1), p=seq(0.01,0.1,0.01))
baselinediff <- list()
for(i in 1:nrow(df)){
thislambda <- df[i,]$lambda
thisp <- df[i,]$p
thisplot <- baseline(foo.t, lambda=thislambda, p=thisp, maxit=20, method='als')
print(paste0("lambda = ", thislambda))
print(paste0("p = ", thisp))
print(paste0("index = ", i))
baselinediff[[i]] <- plot(thisplot)
jpeg(file = paste(baselinediff[[i]], '.jpeg', sep = ''))
dev.off()
}
I know that I would be able to extract corrected spectra using baseline.als but I just want to save the plot images with the red baseline so that I can see how well the baselines are getting drawn. Any baseline users out there that can help?
I suggest you change your loop in the following way:
for(i in 1:nrow(df)){
thislambda <- df[i,]$lambda
thisp <- df[i,]$p
thisplot <- baseline(foo.t, lambda=thislambda, p=thisp, maxit=20, method='als')
print(paste0("lambda = ", thislambda))
print(paste0("p = ", thisp))
print(paste0("index = ", i))
baselinediff[[i]] <- thisplot
jpeg(file = paste('baseline', i, '.jpeg', sep = ''))
plot(baselinediff[[i]])
dev.off()
}
Note that this does not try to capture the already plotted element (thisplot) inside of the list. Instead, the plotting is done after you call the jpeg command. This solves your export issue. Another problem was the naming of the file. If you call baselinediff[[i]] inside of paste, you apparently end up with an error. So I switched it to a simpler name. To plot your resulting list, call:
lapply(baselinediff, plot)
If you are determined on storing the already plotted element, the capture.plotfunction from the imager package might be a good start.

Reset graph at the end of the loop :could not find function "device" error

I am trying to generate plots by looping, here is my code:
n <- unique(wide_data$Product.Code)[1:3]
for (i in n)
{
my.prod2 <- filter(tall_bind, Product.Code == i, Date > ymd("2012/04/01"))
dev.new()
mypath <- file.path("C:","R","SAVEHERE",paste("myplot_", i, ".jpg", sep = ""))
jpeg(file=mypath)
mytitle = paste("Plot for product", i)
p <- qplot(Date, Sold, data = my.prod2, geom = "line", main=mytitle, group = Model, colour = Model) + facet_grid(Model ~ .)
ggsave("myplot_", i, plot=p, device= "jpg" )
}
I get the following error for the above code:
Saving 6.67 x 6.67 in image
Error in ggsave("myplot_", i, plot = p, device = "jpg") : could
not find function "device"
Earlier when I used dev.off() at the end of the loop, I found that though the graphs were being generated they were totally blank.
Could someone please help me understand where is the mistake in my code?
You can leave out the dev.new() and jpg() commands, and also your arguments to ggsave() are incorrect. This should work:
n <- unique(wide_data$Product.Code)[1:3]
for (i in n) {
my.prod2 <- filter(tall_bind, Product.Code == i, Date > ymd("2012/04/01"))
mypath <- file.path("C:","R","SAVEHERE",paste("myplot_", i, ".jpg", sep = ""))
mytitle = paste("Plot for product", i)
p <- qplot(Date, Sold, data = my.prod2, geom = "line", main=mytitle, group = Model, colour = Model) + facet_grid(Model ~ .)
ggsave(filename = mypath, plot = p)
}
What you did was creating a new default graphics device, typically a plotting window, then a jpeg graphics device, i.e. a file. Then you tried to make ggplot2 to plot to directly to file using ggsave, i.e. using its own (jpg) device, and not using either of the two graphics devices you created.
The error, however, was because you gave ggsave the wrong arguments. But even with the right arguments, you would still have ended up with additional unused graphics windows and files through the dev.new() and jpeg() commands. I suggest some extra reading of the help (e.g. type ?ggsave at the r console).
Typically, when using ggplot2 you do not need to worry about dev.new, jpeg and the like. qplot or ggplot and ggsave should do all you need.

Resources