2015-10-01 11 views
8

ggplot2に在庫データをプロットしたり、週末や休日の空白が含まれているx軸をプロットしたりするときに問題が発生する。 this投稿は非常に役に立ちましたが、注文した要素を使用しようとするとさまざまな問題が発生します。ggplot2:x軸の日付から週末と休日の空き領域を削除する

library(xts) 
library(grid) 
library(dplyr) 
library(scales) 
library(bdscale) 
library(ggplot2) 
library(quantmod) 

getSymbols("SPY", from = Sys.Date() - 1460, to = Sys.Date(), adjust = TRUE, auto.assign = TRUE) 

input <- data.frame(SPY["2015/"]) 
names(input) <- c("Open", "High", "Low", "Close", "Volume", "Adjusted") 

# i've tried changing rownames() to index(), and the plot looks good, but the x-axis is inaccurate 
# i've also tried as.factor() 
xaxis <- as.Date(rownames(input)) 
input$xaxis <- xaxis 

p <- ggplot(input) 
p <- p + geom_segment(aes(x = xaxis, xend = xaxis, y = Low, yend = High), size = 0.50)   # body 
p <- p + geom_segment(aes(x = xaxis - 0.4, xend = xaxis, y = Open, yend = Open), size = 0.90) # open 
p <- p + geom_segment(aes(x = xaxis, xend = xaxis + 0.4, y = Close, yend = Close), size = 0.90) # close 
p <- p + scale_y_continuous(scale_y_log10()) 
p + ggtitle("SPY: 2015") 

enter image description here

(サンセリフ赤四角)上記プロットは、上記のコードセグメントと生成されます。次の図は、いくつかのソリューションを試してみる際のいくつかの問題です。まず、データフレームのインデックスを使用しようとすると、私は見栄えの良いグラフを生成しますが、x軸は不正確です。データは現在、10月に終了したが、それ以下のプロットで7月に終了します。 enter image description here

xaxis <- as.Date(index(input)) 

第二に、私が注文した要因にrownamesを強要しようとした場合、私はオープンとを表す(私の横目盛りデータを失いますクローズ)。私は、パッケージbdscaleを使用する場合
enter image description here

xaxis <- factor(rownames(input), ordered = TRUE) 

水平ダニを除去する同じ問題が起こりますが、グリッド線はきれいです:

enter image description here

p <- p + scale_x_bd(business.dates = xaxis) 
+0

、で生産X軸「(サンセリフ赤箱)上記のプロット」に関する不正確な何ですか? – shekeine

+0

赤いボックスは、削除したいx軸のギャップを強調表示します。私は2番目のプロット(ギャップなし)のようなプロットを望みますが、最初のプロットのx軸は – jonnie

+0

です。それで、問題は、休日や週末の自動識別です。作業日だけを保持する 'input'でしょうか? – shekeine

答えて

2

あなたはおそらくする必要があります日付を連続的ではなく離散的な値として扱う。

軸ラベルの治療を更新しました
getSymbols("SPY", from = Sys.Date() - 1460, to = Sys.Date(), adjust = TRUE, auto.assign = TRUE) 
SPY <- SPY["2015/"] 
colnames(SPY) <- sub("SPY.","", colnames(SPY)) 
month_brks <- c(1,endpoints(SPY, "months")[-1]) 

p <- ggplot(data.frame(xaxis=seq(nrow(SPY)), SPY)) 
p <- p + geom_linerange(aes(x=xaxis, ymin=Low, ymax=High), size=.5) 
p <- p + geom_text(aes(x = xaxis, y = Open), size = 4., label="-", hjust=.7, vjust=0) # Open 
p <- p + geom_text(aes(x = xaxis, y = Close), size = 4., label="-", hjust=-.1, vjust=0) # close 
p <- p + scale_x_continuous(breaks=month_brks, labels=format(index(SPY)[month_brks], "%d %b %Y")) 
p <- p + labs(title="SPY: 2015", x="Date", y="Price") 

UPDATE

:あなたのコードを少し簡略化されたバージョンと、このアプローチは、次のようになります。

+0

これは素晴らしいです、ありがとう!私は軸のラベルで遊ぶ必要があります – jonnie

1

まあ、手動で調整することはできますが、それは一種のハッキーです。あなたの観測が続いて188

input$xaxis <-index(as.Date(rownames(input))) 

に1の番号が付けられているので、まず、あなたは、インデックスを使用する必要があり、独自のプロットコード:

p <- ggplot(input) 
p <- p + geom_segment(aes(x = xaxis, xend = xaxis, y = Low, yend = High), size = 0.50)   # body 
p <- p + geom_segment(aes(x = xaxis - 0.4, xend = xaxis, y = Open, yend = Open), size = 0.90) # open 
p <- p + geom_segment(aes(x = xaxis, xend = xaxis + 0.4, y = Close, yend = Close), size = 0.90) # close 
p <- p + scale_y_continuous(scale_y_log10()) + ggtitle("SPY: 2015") 

そして最後に、私は休憩がなされるべき場所を入力して見えました、および手動でラベルを供給:

p + scale_x_continuous(breaks=input$xaxis[c(1,62,125,188)], labels=c("jan","apr","jul","oct")) 

NOTEをここで私は怠け者だったと1月1日が休日であるため、わずか1 1月、1-4月1日 - 7月及び1-10月、最も近い日付を取っていること、ラベル「jan」は2桁の下にあります。そして、ラベル「oct」を30-sep以下に、最後の項目をinputに入れました。あなたはもちろん、これを望むように調整することができます。

もちろん、ラベルを自動化して、ラベルフィールドに日付を追加して月を抽出することもできます。

+0

あなたの出力は最高に見えます!ありがとうございました – jonnie

1

あなただけ多くのグリッド線を使用するように指示し、このためbdscaleを使用したい場合:

ggplot(input) + 
    geom_segment(aes(x = xaxis, xend = xaxis, y = Low, yend = High), size = 0.50) +   # body 
    geom_segment(aes(x = xaxis - 0.4, xend = xaxis, y = Open, yend = Open), size = 0.90) + # open 
    geom_segment(aes(x = xaxis, xend = xaxis + 0.4, y = Close, yend = Close), size = 0.90) + # close 
    ggtitle("SPY: 2015") + 
    xlab('') + ylab('') + 
    scale_x_bd(business.dates=xaxis, max.major.breaks=10, labels=date_format("%b '%y")) # <==== !!!! 

enter image description here

それが軸に10月を置く必要がありますが、それはスマートではありません。 Womp womp。プルのリクエストを歓迎します!

+0

ありがとうございました!最後のx軸のティックに加えて、あなたの実装は、私が保存しようとしている開いていると閉じた横のティックを削除したようです。 – jonnie

+0

あなたは何を意味するか分かります。 'bdscale'のやり方は、あなたの日付をインデックスに変換して日付配列に変換することです。それは偽の連続的なスケールですが、分数はありません。'geom_vline'は軸のスケーリングを回避することを可能にします、' geom_segment'が同じことをする方法があるかどうかを見てみましょう。 – dvmlls

1

以下の方法では、ファセットを使用して不足している日付の間のスペースを削除し、ファセット間の空白を削除して、不安定なプロットの外観を回復します。

まず、日付に区切りがあるたびにインクリメントするグループ化変数を作成します(コードはthis SO answerに適合)。これを後でファセッティングに使用します。

input$group = c(0, cumsum(diff(input$xaxis) > 1)) 

次に、プロットに次のコードを追加します。 facet_gridは、週末または休日のために日付シーケンスに途切れがあった各場所に新しいファセットを作成します。 scale_x_dateは、1週間に1回大きな目盛りを付け、毎日小さな目盛り線を追加しますが、これを調整できます。 theme機能は、ファセットストリップラベルとファセット間の垂直方向のスペースを取り除きます:ここで

p + facet_grid(. ~ group, space="free_x", scales="free_x") + 
    scale_x_date(breaks=seq(as.Date("2015-01-01"),max(input$xaxis), "1 week"), 
       minor_breaks="1 day", 
       labels=date_format("%b %d, %Y")) + 
    theme(axis.text.x=element_text(angle=-90, hjust=0.5, vjust=0.5, size=11), 
     panel.margin = unit(-0.05, "lines"), 
     strip.text=element_text(size=0), 
     strip.background=element_rect(fill=NA)) + 
    ggtitle("SPY: 2015") 

は、得られたプロットです。週末と休日のためのスペースはなくなっています。主要な休憩は毎週マークします。 scale_x_datebreaks引数の週を木曜日に開始するように設定しました。祝日のいずれも木曜日に落ちなかったので、各ファセットには日付の大きな目盛りがあります。 (休日は月曜になることが多いので、月曜日の休暇の週にはデフォルトの区切りが付いた大きな目盛りがありません)。しかし、本来的に主要な休憩間の間隔その週に市場が開かれた日数によって異なります。カスタムgeomが必要と思う -

enter image description here

1

はOHLCが仕事を得ることができませんでした。

あなたが求めているのは正確ではないことは分かっていますが、代わりにおいしいキャンドルチャートであなたを誘惑するかもしれませんか?上記のあなたの質問に

library(dplyr) 
library(bdscale) 
library(ggplot2) 
library(quantmod) 
library(magrittr) 
library(scales) 

getSymbols("SPY", from = Sys.Date() - 1460, to = Sys.Date(), adjust = TRUE, auto.assign = TRUE) 

input <- data.frame(SPY["2015/"]) %>% 
    set_names(c("open", "high", "low", "close", "volume", "adjusted")) %>% 
    mutate(date=as.Date(rownames(.))) 

input %>% ggplot(aes(x=date, ymin=low, ymax=high, lower=pmin(open,close), upper=pmax(open,close), 
        fill=open<close, group=date, middle=pmin(open,close))) + 
    geom_boxplot(stat='identity') + 
    ggtitle("SPY: 2015") + 
    xlab('') + ylab('') + theme(legend.position='none') + 
    scale_x_bd(business.dates=input$date, max.major.breaks=10, labels=date_format("%b '%y")) 

enter image description here

関連する問題