0

I have a data.frame

> head(df,30)
   method  FP TP                    data
1      HF   0  1 A p=10000 n=200 SNR=0.5
2      HM  15  2 A p=10000 n=200 SNR=0.5
3   HMP80   7  2 A p=10000 n=200 SNR=0.5
4   HMP90   2  2 A p=10000 n=200 SNR=0.5
5     LCV   0  2 A p=10000 n=200 SNR=0.5
6    LKSC   0  1 A p=10000 n=200 SNR=0.5
7    LP70   0  1 A p=10000 n=200 SNR=0.5
8    LP85   0  1 A p=10000 n=200 SNR=0.5
9  SS0206   0  0 A p=10000 n=200 SNR=0.5
10 SS0208   0  0 A p=10000 n=200 SNR=0.5
11 SS0406   0  0 A p=10000 n=200 SNR=0.5
12 SS0408   0  0 A p=10000 n=200 SNR=0.5
13 SS0506   0  0 A p=10000 n=200 SNR=0.5
14 SS0508   0  0 A p=10000 n=200 SNR=0.5
15     HF  26  7   A p=10000 n=200 SNR=2
16     HM 137  9   A p=10000 n=200 SNR=2
17  HMP80 136  9   A p=10000 n=200 SNR=2
18  HMP90  64  8   A p=10000 n=200 SNR=2
19    LCV  67  8   A p=10000 n=200 SNR=2
20   LKSC   0  3   A p=10000 n=200 SNR=2
21   LP70  67  8   A p=10000 n=200 SNR=2
22   LP85  51  8   A p=10000 n=200 SNR=2
23 SS0206   0  2   A p=10000 n=200 SNR=2
24 SS0208   0  0   A p=10000 n=200 SNR=2
25 SS0406   0  0   A p=10000 n=200 SNR=2
26 SS0408   0  0   A p=10000 n=200 SNR=2
27 SS0506   0  0   A p=10000 n=200 SNR=2
28 SS0508   0  0   A p=10000 n=200 SNR=2
29     HF  66 16  A p=10000 n=200 SNR=10
30     HM 292 16  A p=10000 n=200 SNR=10

That I am plotting with ggplot2

d = melt(df, id=c("method", "data"))

ggplot() + geom_bar(data=d, aes(x=method, y=value, fill=variable), stat='identity', position='dodge', width=0.5) +
  facet_wrap(~data, ncol=3) +
  theme_bw() + xlab("Method") + ylab("") +
  theme(axis.title.x = element_text(face="bold", colour="#990000", size=20),
          axis.text.x  = element_text(angle=90, vjust=0.5, size=20),
        axis.text.y  = element_text(angle=0, vjust=0.5, size=20),
        legend.text = element_text(colour = 'black', angle = 0, size = 20),
        legend.title = element_text(colour = 'white', angle = 0, size = 20, hjust = 0, vjust = 0))

There are 2 things that I would like to change:

1 - when I plot the order of the faced is defined by the value 'data'. A string with SNR=10 comes before the string with SNR=2. I would like to have the data with SNR=2 before the one with SNR=10

2- I would like a different scale on each facet. (Now in each facet y goes from 0 to almost 300. )

How can I change this?

EDIT:

I have found a solution to the first problem

u = unique(df$data) 
levels(u) = u 
d$data = factor(df$data, levels=levels(u))

Regarding the second problem I am using the option

 facet_wrap(~data, ncol=3, scales = 'free_y') 

But the problem is that I would like only integer values on the axis. I have tried scale_y_discrete() but in this case too many values are plotted in some facets. How can I solve this?

EDIT :

This is my current R code. I have tried the scales packages but I do not understand how to use it in my situation.

df = read.csv(file = "Desktop/n200_p10000.csv")
df$method.1 = NULL
df$score = NULL
df$FN = NULL
df$TN = NULL
d = melt(df, id=c("method", "data"))

u = unique(df$data)
levels(u) = u

d$data = factor(df$data, levels=levels(u))

ggplot() + geom_bar(data=d, aes(x=method, y=value, fill=variable), stat='identity', position='dodge', width=0.5) +
  facet_wrap(~data, ncol=3, scales = 'free_y') +
  scale_y_continuous() + 
  theme_bw() + xlab("Method") + ylab("") +
  theme(axis.title.x = element_text(face="bold", colour="#990000", size=20),
          axis.text.x  = element_text(angle=90, vjust=0.5, size=20),
        axis.text.y  = element_text(angle=0, vjust=0.5, size=20),
        legend.text = element_text(colour = 'black', angle = 0, size = 20),
        legend.title = element_text(colour = 'white', angle = 0, size = 20, hjust = 0, vjust = 0))
tonytonov
  • 25,060
  • 16
  • 82
  • 98
Donbeo
  • 17,067
  • 37
  • 114
  • 188

1 Answers1

1

To manipulate the order of facets, you need the levels of the factor you are faceting on to be sorted as you want. So you need to order the levels of data. This can be done for example like df$data <- factor(df$data, levels = c(...)) (with your desired order of levels in c()).

Regarding your second question, look at ?facet_wrap and in particular the scales option. You will have to set scales = 'free' or 'free_y'.

To have only integer values on the axis, try using the package scales, together with the argument labels in scale_y_continuous(). You can use one of the predefined formats that come with the package, or define your own, for example

intfmt <- function(x) format(x, digits = 0)

will only print the integer part of a number. After specifying this, you just need to add the following line to your ggplot call

+ scale_y_continuous(labels = intfmt)
konvas
  • 14,126
  • 2
  • 40
  • 46
  • the free y option works. The problem with the order is that I have to many levels. I can not specify them one by one. – Donbeo Jul 12 '14 at 16:55
  • `sort` will not work because you are sorting strings rather than numbers, and as strings "10" comes before "2". So you either have to specify it manually, or you have to code a `for` loop that prints them in the order you want and then you copy-paste it into your code. I don't know a way to sort these strings that will sort them like they were numbers, other than using `as.numeric`, which doesn't work in your case because you have text mixed with numbers. – konvas Jul 12 '14 at 17:05
  • This can be done with the `scales` package - see updated answer. – konvas Jul 12 '14 at 21:47
  • sorry but I do not understand how to use scales in my situation. My whole code is in the question now. – Donbeo Jul 14 '14 at 07:38
  • Sorry but I am still unhappy. In this way the 1.5 values are replaced with 1. So on the y axis I have labels 0, 0, 1, 1, 2 .... I would like to have just 0, 1, 2 – Donbeo Jul 14 '14 at 11:31
  • In that case you need to specify the breaks, so that they are spaced better. Have a look at the answer to this question http://stackoverflow.com/questions/5380417/is-there-a-way-of-manipulating-ggplot-scale-breaks-and-labels – konvas Jul 14 '14 at 12:13