简体   繁体   English

多时间序列图中的标签X轴

[英]Label X Axis in Multiple Time Series Plot

I have plotted three time series graphs on three separate screens. 我在三个不同的屏幕上绘制了三个时间序列图。 All works fine apart from the x-axis will not plot what I'm asking it to. 除x轴外,所有工作均正常,不会绘制我要的内容。

I have used the code from this Stack Overflow question , which worked for one screen, ie all three graphs on one screen, but it refuses to register on the three screen format with no error messages. 我已经使用了这个Stack Overflow问题中的代码, 该问题适用于一个屏幕,即所有三个图形都位于一个屏幕上,但是它拒绝在三个屏幕格式上注册,而没有任何错误消息。

dev.new()
plot(tp,screens=c(1,2,3),col=c("deepskyblue","seagreen3","orchid4"),ylim=c(0,1600),lwd="3",ylab=(expression("TP"~~(mu*"g/L"))),xlab=NA,
main="Seasonal variation of total phosphorus in Water Friendly Farming catchments",cex.main=2,xaxt="n")
legend(locator(1),legend=c("Barkby Brook","Eye Brook","Stonton Brook"),fill=c("deepskyblue","seagreen3","orchid4"),bty="n")
times<-time(tp)
ticks<-seq(times[1],times[length(times)],by=90)
axis(1,at=ticks,labels=c("Spring 2012","Summer 2012","Autumn 2012","Winter 2012","Spring 2013","Summer 2013","Autumn 2013","Winter 2013","Spring 2014"))

TP stands for total phosphorus at three sites, I have merged three zoo objects to obtain it. TP代表三个地点的总磷,我已经合并了三个动物园对象以获得它。 I then merged the zoo object to a separate zero width zoo object which contains dates from 2012-03-26 to 2014-04-13. 然后,我将Zoo对象合并到一个单独的零宽度Zoo对象,该对象包含从2012-03-26到2014-04-13的日期。

DATA: 数据:

mydata<-structure(list(date = structure(c(16054, 15783, 16139, 15528, 
15615, 15726, 15957, 16155, 15922, 16013, 16105, 15594, 15687, 
16012, 15614, 15684, 16041, 15533, 15841, 16055, 16064, 15916, 
15522, 15621, 16065, 15759, 15868, 16156, 15830, 15629), class = "Date"), 
month = structure(c(7L, 17L, 18L, 12L, 22L, 10L, 25L, 18L, 
5L, 21L, 9L, 24L, 6L, 21L, 22L, 6L, 7L, 12L, 19L, 7L, 7L, 
13L, 12L, 22L, 7L, 8L, 15L, 18L, 19L, 22L), .Label = c("April.2012", 
"April.2013", "April.2014", "Aug.2012", "Aug.2013", "Dec.2012", 
"Dec.2013", "Feb.2013", "Feb.2014", "Jan.2013", "Jan.2014", 
"July.2012", "July.2013", "June.2012", "June.2013", "March.2012", 
"March.2013", "March.2014", "May.2013", "Nov.2012", "Nov.2013", 
"Oct.2012", "Oct.2013", "Sept.2012", "Sept.2013"), class = "factor"), 
year = c(2013L, 2013L, 2014L, 2012L, 2012L, 2013L, 2013L, 
2014L, 2013L, 2013L, 2014L, 2012L, 2012L, 2013L, 2012L, 2012L, 
2013L, 2012L, 2013L, 2013L, 2013L, 2013L, 2012L, 2012L, 2013L, 
2013L, 2013L, 2014L, 2013L, 2012L), tp.barkby = c(200.74, 
103.32, 65.6, NA, 94.37, NA, 1110.46, 105.87, NA, 63.68, 
87, 266.29, NA, 114.62, 184.21, 87.95, 148.81, NA, NA, 204.81, 
138.38, 298.48, 120.8, 146.8, 96.6, 91.16, 384.18, 94.16, 
141.72, 125), tp.eyebrook = c(117.59, 101.74, 102.35, 180, 
131.74, NA, 232.5, 144.82, 487.23, 105.26, 95.75, 250.1, 
NA, 99.93, 144.37, 87.95, 107.14, NA, 105.41, 489.33, 147.91, 
132.52, 105.6, 108.8, 111, 76.95, 193, 130.74, 113.17, 134
), tp.stonton = c(85.2, 99.9, 94.85, NA, 54.9, 79.68, 168.86, 
170.08, 284.05, 133.95, 80.5, 102, NA, NA, 61.21, NA, 68.1, 
NA, 107.23, 367.19, 152.91, 131.33, 79.2, 67.8, 88.26, 56.16, 
151.68, 161.79, 61.5, 272)), .Names = c("date", "month",
"year", "tp.barkby", "tp.eyebrook", "tp.stonton"), row.names = c(582L, 
 311L, 667L, 56L, 143L, 254L, 485L, 683L, 450L, 541L, 633L, 122L, 
215L, 540L, 142L, 212L, 569L, 61L, 369L, 583L, 592L, 444L, 50L, 
149L, 593L, 287L, 396L, 684L, 358L, 157L), class = "data.frame")

mydata$date<-as.Date(mydata$date)
attach(mydata)
str(mydata)
library(zoo)
#Total Phosphorus
#1 - create a zero-width (dataless) zoo object with the missing dates/times.
dates<-seq(from=as.Date("2012-03-26"), to=as.Date("2014-04-13"), by=1)
empty<-zoo(,dates)
#2 - create zoo objects from the data
ts.tpb<-zoo(tp.barkby,date)
ts.tpe<-zoo(tp.eyebrook,date)
ts.tps<-zoo(tp.stonton,date)
#3 - merge the zoo objects and apply na.approx
merged.tp<-na.approx(merge(ts.tpb,ts.tpe,ts.tps))
#4 - merge the dataless with the datafull 
tp<-na.approx(merge(merged.tp,empty,all=TRUE))
#Three screen plot
dev.new()
plot(tp,screens=c(1,2,3),col=c("deepskyblue","seagreen3","orchid4"),ylim=c(0,1600),lwd="3",    ylab=(expression("TP"~~(mu*"g/L"))),xlab=NA,
main="Seasonal variation of total phosphorus in Water Friendly Farming     
catchments",cex.main=2,xaxt="n")
legend(locator(1),legend=c("Barkby Brook","Eye Brook","Stonton             
Brook"),fill=c("deepskyblue","seagreen3","orchid4"),bty="n")
times<-time(tp)
ticks<-seq(times[1],times[length(times)],by=90)
axis(1,at=ticks,labels=c("Spring 2012","Summer 2012","Autumn 2012","Winter     2012","Spring 2013","Summer 2013","Autumn 2013","Winter 2013","Spring 2014"))
#Axis at and labels will differ as this is not the whole dataset

I hope that helps....... 我希望能有所帮助.......

Next time when posing a question please cut down your code down to a reasonable size getting rid of all the parts that are not really related to the question. 下次在提出问题时,请将代码缩减为合理的大小,以消除与该问题无关的所有部分。

There are lots of examples of how to do this in the examples section of ?plot.zoo .( link ) Define a panel function and put your code in there. ?plot.zoo的示例部分中,有很多关于如何执行此操作的示例。( link )定义一个面板函数并将代码放入其中。 For example, using the setup in the question 例如,使用问题中的设置

pnl <- function(x, y, ...) {

  lines(y ~ x)

  panel.number = parent.frame()$panel.number
  nser <- parent.frame()$nser
  if (panel.number == nser) {
     ticks <- seq(x[1], x[length(x)], by=90)
     axis(1, at = ticks, labels = letters[seq_along(ticks)])
  }
}

plot(tp, panel = pnl, xaxt = "n")

在此处输入图片说明

2) zoo also supports lattice plots and ggplot2 plots. 2) zoo还支持点阵图和ggplot2图。 Here is a ggplot2 plot via autoplot.zoo ( link ) 这是通过autoplot.zoo的ggplot2图( link

library(ggplot2)
at <- seq(start(tp), end(tp), by = 90)
autoplot(tp) + scale_x_date(breaks = at, labels = letters[seq_along(at)])

屏幕截图

you are trying to coerce text labels on a date axis hence there is no output. 您试图在date轴上强制text标签,因此没有输出。 For custom text labels you need to convert xts/zoo to data.frame before plotting, plot data without any time index and provide custom labels in axis(1,...) 对于自定义文本标签,您需要在绘制之前将xts/zoo转换为data.frame ,绘制没有任何时间索引的数据,并在axis(1,...)提供自定义标签

Code

With sample xts data 使用样本XTS数据

#Load sample xts/zoo data, lubridate for month/year functions

require(PerformanceAnalytics)
require(lubridate)
data(edhec)

#Convert to data.frame for plotting, keep data until Dec 1998 and single time series 

df<-data.frame(date=index(edhec[,1]['/1998']),edhec[,1]['/1998'],row.names=NULL)


#label break dates,monthly data,hence seq index = 3

ticks<-df$date[seq(1,length(df$date),3)]

#label breaks, at = seq(1,length(df$date),3)

#Map months to seasons (USA)
Month2Season<-function(mon){

Winter<-c(12,1,2)
Spring<-c(3,4,5)
Summer<-c(6,7,8)
Autumn<-c(9,10,11)

season<-NULL

if      (any(mon %in% Winter)) season="Winter"  
else if (any(mon %in% Spring)) season="Spring" 
else if (any(mon %in% Summer)) season="Summer" 
else if (any(mon %in% Autumn)) season="Autumn" 

return(season)
}

#get seasons for all label break dates

season_labels<-sapply(ticks,function(x) paste0(Month2Season(month(x)),"-",year(x)))

# provide numeric index for label breaks of at =

plot(df$Convertible.Arbitrage,type="l",xaxt="n")
axis(1,at=seq(1,length(df$date),3),labels=season_labels)

Plot 情节 在此处输入图片说明

Unfortunately the default plot.zoo function internally changes par settings when you plot multiple plots and then automatically resets them when the function exists. 不幸的是,当您绘制多个图时,默认的plot.zoo函数会在内部更改par设置,然后在该函数存在时自动将其重置。 When it resets the par parameters, this resets the plotting surface so subsequent calls to axis do not work. 重置par参数时,这将重置绘图表面,因此后续对axis调用将不起作用。 This function does not do this when only drawing a single time series. 仅绘制单个时间序列时,此功能不会执行此操作。

There is no super easy/robust way to fix this. 没有超级简单/稳健的方法可以解决此问题。 But, if you are feeling bold, you can perform a surgery on the function and insert new code in there. 但是,如果您感到胆怯,则可以对该函数进行手术,然后在其中插入新代码。 (This is not a generally recommended practice, but in this case it will make your life easier). (这不是一般推荐的做法,但是在这种情况下,它将使您的生活更轻松)。 I did this with zoo version 1.7-10. 我使用的是1.7-10版的动物园。 To make sure this will work for you, check that 为确保此方法适合您,请检查

body(plot.zoo)[19:20]

returns 退货

do.call("title", title.args)(return(invisible(x)))

because we are going to add a line of code between those two statements. 因为我们要在这两个语句之间添加一行代码。 We will do that with 我们将这样做

plot.zoo2<-plot.zoo
bl<-as.list(body(plot.zoo2))
bl<-c(
    bl[1:19], 
    quote(axis(1,at=ticks,labels=tick.lables)), 
    bl[20]
)
body(plot.zoo2)<-as.call(bl)

We've actually created a new function called plot.zoo2 that adds in a call to axis with our desired values. 实际上,我们已经创建了一个名为plot.zoo2的新函数,该函数添加了对具有所需值的axis的调用。 Now we call almost the same way we would the normal plotting function, but we just use our new version instead. 现在,我们以与普通绘图功能几乎相同的方式进行调用,但是我们只使用新版本。

#define these before the plot() since we use them in our function now
times<-time(tp)
ticks<-seq(times[1],times[length(times)],by=90)
tick.labels<-c("Spring 2012","Summer 2012","Autumn 2012","Winter     2012","Spring 2013","Summer 2013","Autumn 2013","Winter 2013")

plot.zoo2(tp,screens=c(1,2,3),
    col=c("deepskyblue","seagreen3","orchid4"),
    ylim=c(0,1600),lwd="3",
    ylab=(expression("TP"~~(mu*"g/L"))),xlab=NA,xaxt="n",
    main="Seasonal variation of total phosphorus",
    cex.main=2)

Which gives 这使

样本结果

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM