2015-05-02 27 views
7

data.frame中,我有一個文本語言的分類變量。但是,雖然大多數文本只能使用一種語言,但有些使用多種語言。在我的數據,它們出現在同一列,用逗號分隔:R - 在一個變量中將多個值作爲一個字符串處理

text = c("Text1", "Text2", "Text3") 
lang = c("fr", "en", "fr,en") 
d = data.frame(text, lang) 

視覺:

text lang 
1 Text1 fr 
2 Text2 en 
3 Text3 fr,en 

我想繪製文本的數量在每一種語言,用文本3被同時統計在fren中。

我發現如何分割,與:

d$lang <- strsplit(d$lang, ",") 

但我無法找到一個方法來正確地繪製它,例如用qplot barplot像這樣的:

qplot(lang, data=d) 

我這樣做對嗎?有更好的方法嗎?

+3

你不能將一個列表傳遞給'qplot',它的默認圖是散點圖。嘗試使用'qplot(x = unlist(strsplit(as.character(d $ lang),「,」)),geom =「bar」)'或者爲''greplot''應答。'barplot(table(unlist(strsplit (as.character(d $ lang),「,」))))'或 – user20650

+0

非常感謝。 有沒有辦法在維護其他數據列時使用'unlist'? 在上面的例子中,假設我還有第三列,我想保持與lang對齊,有沒有辦法?也許通過重複觀察? –

回答

6

你可以嘗試:

library(splitstackshape) 
dl <- cSplit(d, "lang", ",", "long") 
qplot(lang, data = dl) 
+0

現在我明白了......! (閱讀'splitstackshape'文檔後:-)) 該軟件包非常完美:非常感謝! 確實,我需要的是:**'cSplit(d,「lang」)'**,它與'cSplit(d,「lang」,「,」,「wide」)相同' –

1

考慮tidyr::separate()拆分和tidyr::gather()使它長。

library(magrittr) 
ceiling <- 2L #The max language count of any single text 
language_positions <- paste0("language_", seq_len(ceiling)) 

d %>% 
    tidyr::separate("lang", language_positions, sep=",", extra="merge") %>% 
    tidyr::gather_("ordinal", "language_name", language_positions) %>% 
    dplyr::filter(!is.na(language_name)) 

產生的長期數據集:

text ordinal language_name 
1 Text1 language_1   fr 
2 Text2 language_1   en 
3 Text3 language_1   fr 
4 Text3 language_2   en 

如果你想它分成兩個較小的步驟。該separate()創建了一個廣泛的數據集,

> d_wide <- d %>% 
+ tidyr::separate_("lang", language_positions, sep=",", extra="merge") 
> d_wide 
    text language_1 language_2 
1 Text1   fr  <NA> 
2 Text2   en  <NA> 
3 Text3   fr   en 

...然後gather()其轉換爲高。

d_long <- d_wide %>% 
    tidyr::gather_("ordinal", "language_name", language_positions) %>% 
    dplyr::filter(!is.na(language_name)) 

其他原因,我建議增加, stringsAsFactors=F當你定義d,但的tidyr獨立的功能似乎並不介意做。 qplot調用可以保持不變:qplot(language_name, data=d_long)

2

沒有按照user20650的意見建議,你可能就無法脫身,而不重組你的數據,你如何做到這一點,不能盲目的方式數據被任意存儲。例如,如果知道語言是由不同的,兩個字符的字符串表示的(例如,任何不是「fr」的語言表示都不包含序列「fr」),您可以創建新的布爾列基於在逗號分隔表示中搜索代碼。例如:

# Data 
text = c("Text1", "Text2", "Text3", "Text4", "Text5") 
lang = c("fr", "en", "fr,en", "sp,fr", "sp,fr,en") 
d = data.frame(text, lang, stringsAsFactors = FALSE) 

# Get a vector of the languages that exist 
languages <- unique(unlist(strsplit(d$lang, ","))) 

# Create a new column for each language 
for (language in languages) d[[language]] <- grepl(language, d$lang) 

# An example bar-plot 
barplot(colSums(d[, -c(1, 2)])) 
+0

謝謝許多。我花了一些時間來充分理解你的答案(因爲我對R的基本理解),但現在我確實瞭解,這正是我所需要的。 :) –

相關問題