1 序章

概要

<ポイント>
- データフレームの操作に特化したパッケージ
- C++で書かれているため処理が高速 (plyrパッケージと比較)
- パイプ(%>%)との相性が良い



登録関数

# 登録数
ls("package:dplyr") %>% length()
[1] 236
# 関数一覧
ls("package:dplyr") %>% print()
  [1] "%>%"                "add_count"          "add_count_"        
  [4] "add_row"            "add_rownames"       "add_tally"         
  [7] "add_tally_"         "all_equal"          "all_vars"          
 [10] "anti_join"          "any_vars"           "arrange"           
 [13] "arrange_"           "arrange_all"        "arrange_at"        
 [16] "arrange_if"         "as.tbl"             "as.tbl_cube"       
 [19] "as_data_frame"      "as_tibble"          "auto_copy"         
 [22] "band_instruments"   "band_instruments2"  "band_members"      
 [25] "bench_tbls"         "between"            "bind_cols"         
 [28] "bind_rows"          "case_when"          "changes"           
 [31] "check_dbplyr"       "coalesce"           "collapse"          
 [34] "collect"            "combine"            "common_by"         
 [37] "compare_tbls"       "compare_tbls2"      "compute"           
 [40] "contains"           "copy_to"            "count"             
 [43] "count_"             "cumall"             "cumany"            
 [46] "cume_dist"          "cummean"            "current_vars"      
 [49] "data_frame"         "data_frame_"        "db_analyze"        
 [52] "db_begin"           "db_commit"          "db_create_index"   
 [55] "db_create_indexes"  "db_create_table"    "db_data_type"      
 [58] "db_desc"            "db_drop_table"      "db_explain"        
 [61] "db_has_table"       "db_insert_into"     "db_list_tables"    
 [64] "db_query_fields"    "db_query_rows"      "db_rollback"       
 [67] "db_save_query"      "db_write_table"     "dense_rank"        
 [70] "desc"               "dim_desc"           "distinct"          
 [73] "distinct_"          "do"                 "do_"               
 [76] "ends_with"          "enquo"              "eval_tbls"         
 [79] "eval_tbls2"         "everything"         "explain"           
 [82] "failwith"           "filter"             "filter_"           
 [85] "filter_all"         "filter_at"          "filter_if"         
 [88] "first"              "frame_data"         "full_join"         
 [91] "funs"               "funs_"              "glimpse"           
 [94] "group_by"           "group_by_"          "group_by_all"      
 [97] "group_by_at"        "group_by_if"        "group_by_prepare"  
[100] "group_indices"      "group_indices_"     "group_size"        
[103] "group_vars"         "grouped_df"         "groups"            
[106] "id"                 "ident"              "if_else"           
[109] "inner_join"         "intersect"          "is.grouped_df"     
[112] "is.src"             "is.tbl"             "is_grouped_df"     
[115] "lag"                "last"               "lead"              
[118] "left_join"          "location"           "lst"               
[121] "lst_"               "make_tbl"           "matches"           
[124] "min_rank"           "mutate"             "mutate_"           
[127] "mutate_all"         "mutate_at"          "mutate_each"       
[130] "mutate_each_"       "mutate_if"          "n"                 
[133] "n_distinct"         "n_groups"           "na_if"             
[136] "nasa"               "near"               "nth"               
[139] "ntile"              "num_range"          "one_of"            
[142] "order_by"           "percent_rank"       "progress_estimated"
[145] "pull"               "quo"                "quo_name"          
[148] "quos"               "rbind_all"          "rbind_list"        
[151] "recode"             "recode_factor"      "rename"            
[154] "rename_"            "rename_all"         "rename_at"         
[157] "rename_if"          "rename_vars"        "rename_vars_"      
[160] "right_join"         "row_number"         "rowwise"           
[163] "same_src"           "sample_frac"        "sample_n"          
[166] "select"             "select_"            "select_all"        
[169] "select_at"          "select_if"          "select_var"        
[172] "select_vars"        "select_vars_"       "semi_join"         
[175] "setdiff"            "setequal"           "show_query"        
[178] "slice"              "slice_"             "sql"               
[181] "sql_escape_ident"   "sql_escape_string"  "sql_join"          
[184] "sql_select"         "sql_semi_join"      "sql_set_op"        
[187] "sql_subquery"       "sql_translate_env"  "src"               
[190] "src_df"             "src_local"          "src_mysql"         
[193] "src_postgres"       "src_sqlite"         "src_tbls"          
[196] "starts_with"        "starwars"           "storms"            
[199] "summarise"          "summarise_"         "summarise_all"     
[202] "summarise_at"       "summarise_each"     "summarise_each_"   
[205] "summarise_if"       "summarize"          "summarize_"        
[208] "summarize_all"      "summarize_at"       "summarize_each"    
[211] "summarize_each_"    "summarize_if"       "tally"             
[214] "tally_"             "tbl"                "tbl_cube"          
[217] "tbl_df"             "tbl_nongroup_vars"  "tbl_sum"           
[220] "tbl_vars"           "tibble"             "top_n"             
[223] "transmute"          "transmute_"         "transmute_all"     
[226] "transmute_at"       "transmute_if"       "tribble"           
[229] "trunc_mat"          "type_sum"           "ungroup"           
[232] "union"              "union_all"          "vars"              
[235] "with_order"         "wrap_dbplyr_obj"   



2 準備編

パイプ演算子

概要

1. パイプのメリット

- パイプ(%>%)を使うと人間の思考回路とコードの流れが近くなる
- 関数と引数の位置が近くなるので視認性が大幅に向上
- {dplyr}自体がパイプ操作を前提に設計されていて親和性が高い
- Rstudioではパイプ(%>%)のショートカットは「Ctrl + Shift + M」


2. {dplyr}との親和性

- 第一引数がdata.frameとなっていてパイプ(%>%)が使いやすい
- 第二引数以降で「$」を使わずに列指定できるのはパイプ(%>%)がもたらすメリット
- 戻り値がdata.frameとなっていてパイプ(%>%)が使いやすい



パイプなし(変数でつなぐ)

# 変数がたくさん登場するので見にくい(最悪)
a1 <- group_by(flights, year, month, day)
a2 <- select(a1, arr_delay, dep_delay)
a3 <- summarise(a2,
                arr = mean(arr_delay, na.rm = TRUE),
                dep = mean(dep_delay, na.rm = TRUE))
a4 <- filter(a3, arr > 30 | dep > 30)
a4



パイプなし(関数をネスト)

# ネストが深くなるにつれて関数の要素が分断される(イマイチ)
filter(
  summarise(
    select(
      group_by(flights, year, month, day),
      arr_delay, dep_delay
    ),
    arr = mean(arr_delay, na.rm = TRUE),
    dep = mean(dep_delay, na.rm = TRUE)
  ),
  arr > 30 | dep > 30
)



パイプを使った操作

# 人間の思考回路に沿った書き方で見やすい!
flights %>%
  group_by(year, month, day) %>%
  select(arr_delay, dep_delay) %>%
  summarise(
    arr = mean(arr_delay, na.rm = TRUE),
    dep = mean(dep_delay, na.rm = TRUE)) %>%
  filter(arr > 30 | dep > 30)



パッケージの優先順位

概要

<ポイント>

- パッケージ間で関数名が重複すると、パッケージの優先順位が問題となる
- Rが関数を混同せずに使うには、優先順位のコントロールが必要
- パッケージ指定(dplyr::)もできるが、オートコンプリートが使えなくなる弊害あり


<名前空間>

- ロードしているパッケージには優先順位が存在する(名前空間)
- 名前空間の優先順位はsearch関数で確認できる
- {needs}のprioritize関数を使うと、指定したパッケージの優先順位を1番にできる
- prioritize関数はパッケージを一度デタッチして、再度参照させている



needsパッケージ

<優先順位コントロール>

needsパッケージのprioritize関数で、dplyrパッケージの優先順位を最上位にする  
{dplyr}の関数群が最優先となる
# パッケージの優先順位の確認
search()
##  [1] ".GlobalEnv"           "package:xts"          "package:zoo"         
##  [4] "package:RcppRoll"     "package:nycflights13" "package:lubridate"   
##  [7] "package:dplyr"        "package:purrr"        "package:readr"       
## [10] "package:tidyr"        "package:tibble"       "package:ggplot2"     
## [13] "package:tidyverse"    "package:magrittr"     "package:rmarkdown"   
## [16] "package:knitr"        "package:stats"        "package:graphics"    
## [19] "package:grDevices"    "package:utils"        "package:datasets"    
## [22] "package:methods"      "Autoloads"            "package:base"
# needsパッケージのロード
library("needs")

# {dplyr}を優先順位が1番になるように操作
prioritize("dplyr")

# パッケージの優先順位の再確認
search()
##  [1] ".GlobalEnv"           "package:dplyr"        "package:needs"       
##  [4] "package:xts"          "package:zoo"          "package:RcppRoll"    
##  [7] "package:nycflights13" "package:lubridate"    "package:purrr"       
## [10] "package:readr"        "package:tidyr"        "package:tibble"      
## [13] "package:ggplot2"      "package:tidyverse"    "package:magrittr"    
## [16] "package:rmarkdown"    "package:knitr"        "package:stats"       
## [19] "package:graphics"     "package:grDevices"    "package:utils"       
## [22] "package:datasets"     "package:methods"      "Autoloads"           
## [25] "package:base"



fligtデータセットの確認

概要

<概要>

- 2013年にニューヨーク市から出発した飛行機のデータ(約33万件)
- fligtsデータセットは「tbl_df」というクラスで定義されている
    - {dplyr}のtbl_df関数で変換できる
    - {dplyr}のdata_frame関数で定義できる
    - 最初の10レコードのみが表示(誤って大量データがコンソールに表示されない)



データセットの確認

# データセットの確認
flights %>% glimpse()
## Observations: 336,776
## Variables: 19
## $ year           <int> 2013, 2013, 2013, 2013, 2013, 2013, 2013, 2013,...
## $ month          <int> 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,...
## $ day            <int> 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,...
## $ dep_time       <int> 517, 533, 542, 544, 554, 554, 555, 557, 557, 55...
## $ sched_dep_time <int> 515, 529, 540, 545, 600, 558, 600, 600, 600, 60...
## $ dep_delay      <dbl> 2, 4, 2, -1, -6, -4, -5, -3, -3, -2, -2, -2, -2...
## $ arr_time       <int> 830, 850, 923, 1004, 812, 740, 913, 709, 838, 7...
## $ sched_arr_time <int> 819, 830, 850, 1022, 837, 728, 854, 723, 846, 7...
## $ arr_delay      <dbl> 11, 20, 33, -18, -25, 12, 19, -14, -8, 8, -2, -...
## $ carrier        <chr> "UA", "UA", "AA", "B6", "DL", "UA", "B6", "EV",...
## $ flight         <int> 1545, 1714, 1141, 725, 461, 1696, 507, 5708, 79...
## $ tailnum        <chr> "N14228", "N24211", "N619AA", "N804JB", "N668DN...
## $ origin         <chr> "EWR", "LGA", "JFK", "JFK", "LGA", "EWR", "EWR"...
## $ dest           <chr> "IAH", "IAH", "MIA", "BQN", "ATL", "ORD", "FLL"...
## $ air_time       <dbl> 227, 227, 160, 183, 116, 150, 158, 53, 140, 138...
## $ distance       <dbl> 1400, 1416, 1089, 1576, 762, 719, 1065, 229, 94...
## $ hour           <dbl> 5, 5, 5, 5, 6, 5, 6, 6, 6, 6, 6, 6, 6, 6, 6, 5,...
## $ minute         <dbl> 15, 29, 40, 45, 0, 58, 0, 0, 0, 0, 0, 0, 0, 0, ...
## $ time_hour      <dttm> 2013-01-01 05:00:00, 2013-01-01 05:00:00, 2013...
# データセットの大きさ
flights %>% head()
## # A tibble: 6 x 19
##    year month   day dep_time sched_dep_time dep_delay arr_time
##   <int> <int> <int>    <int>          <int>     <dbl>    <int>
## 1  2013     1     1      517            515         2      830
## 2  2013     1     1      533            529         4      850
## 3  2013     1     1      542            540         2      923
## 4  2013     1     1      544            545        -1     1004
## 5  2013     1     1      554            600        -6      812
## 6  2013     1     1      554            558        -4      740
## # ... with 12 more variables: sched_arr_time <int>, arr_delay <dbl>,
## #   carrier <chr>, flight <int>, tailnum <chr>, origin <chr>, dest <chr>,
## #   air_time <dbl>, distance <dbl>, hour <dbl>, minute <dbl>,
## #   time_hour <dttm>




{dplyr}のデータセット

nasa

nasa %>% glimpse()
## List of 2
##  $ mets:List of 7
##   ..$ cloudhigh  : num [1:24, 1:24, 1:12, 1:6] 26 20 16 13 7.5 8 14.5 19.5 22.5 21 ...
##   ..$ cloudlow   : num [1:24, 1:24, 1:12, 1:6] 7.5 11.5 16.5 20.5 26 30 29.5 26.5 27.5 26 ...
##   ..$ cloudmid   : num [1:24, 1:24, 1:12, 1:6] 34.5 32.5 26 14.5 10.5 9.5 11 17.5 18.5 16.5 ...
##   ..$ ozone      : num [1:24, 1:24, 1:12, 1:6] 304 304 298 276 274 264 258 252 250 250 ...
##   ..$ pressure   : num [1:24, 1:24, 1:12, 1:6] 835 940 960 990 1000 1000 1000 1000 1000 1000 ...
##   ..$ surftemp   : num [1:24, 1:24, 1:12, 1:6] 273 280 285 289 292 ...
##   ..$ temperature: num [1:24, 1:24, 1:12, 1:6] 272 282 285 291 293 ...
##  $ dims:List of 4
##   ..$ lat  : num [1:24] 36.2 33.7 31.2 28.7 26.2 ...
##   ..$ long : num [1:24] -114 -111 -109 -106 -104 ...
##   ..$ month: int [1:12] 1 2 3 4 5 6 7 8 9 10 ...
##   ..$ year : int [1:6] 1995 1996 1997 1998 1999 2000
##  - attr(*, "class")= chr "tbl_cube"



starwars

starwars %>% glimpse()
## Observations: 87
## Variables: 13
## $ name       <chr> "Luke Skywalker", "C-3PO", "R2-D2", "Darth Vader", ...
## $ height     <int> 172, 167, 96, 202, 150, 178, 165, 97, 183, 182, 188...
## $ mass       <dbl> 77.0, 75.0, 32.0, 136.0, 49.0, 120.0, 75.0, 32.0, 8...
## $ hair_color <chr> "blond", NA, NA, "none", "brown", "brown, grey", "b...
## $ skin_color <chr> "fair", "gold", "white, blue", "white", "light", "l...
## $ eye_color  <chr> "blue", "yellow", "red", "yellow", "brown", "blue",...
## $ birth_year <dbl> 19.0, 112.0, 33.0, 41.9, 19.0, 52.0, 47.0, NA, 24.0...
## $ gender     <chr> "male", NA, NA, "male", "female", "male", "female",...
## $ homeworld  <chr> "Tatooine", "Tatooine", "Naboo", "Tatooine", "Alder...
## $ species    <chr> "Human", "Droid", "Droid", "Human", "Human", "Human...
## $ films      <list> [<"Revenge of the Sith", "Return of the Jedi", "Th...
## $ vehicles   <list> [<"Snowspeeder", "Imperial Speeder Bike">, <>, <>,...
## $ starships  <list> [<"X-wing", "Imperial shuttle">, <>, <>, "TIE Adva...



storms

storms %>% glimpse()
## Observations: 10,010
## Variables: 13
## $ name        <chr> "Amy", "Amy", "Amy", "Amy", "Amy", "Amy", "Amy", "...
## $ year        <dbl> 1975, 1975, 1975, 1975, 1975, 1975, 1975, 1975, 19...
## $ month       <dbl> 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 6, 7,...
## $ day         <int> 27, 27, 27, 27, 28, 28, 28, 28, 29, 29, 29, 29, 30...
## $ hour        <dbl> 0, 6, 12, 18, 0, 6, 12, 18, 0, 6, 12, 18, 0, 6, 12...
## $ lat         <dbl> 27.5, 28.5, 29.5, 30.5, 31.5, 32.4, 33.3, 34.0, 34...
## $ long        <dbl> -79.0, -79.0, -79.0, -79.0, -78.8, -78.7, -78.0, -...
## $ status      <chr> "tropical depression", "tropical depression", "tro...
## $ category    <ord> -1, -1, -1, -1, -1, -1, -1, -1, 0, 0, 0, 0, 0, 0, ...
## $ wind        <int> 25, 25, 25, 25, 25, 25, 25, 30, 35, 40, 45, 50, 50...
## $ pressure    <int> 1013, 1013, 1013, 1013, 1012, 1012, 1011, 1006, 10...
## $ ts_diameter <dbl> NA, NA, NA, NA, NA, NA, NA, NA, NA, NA, NA, NA, NA...
## $ hu_diameter <dbl> NA, NA, NA, NA, NA, NA, NA, NA, NA, NA, NA, NA, NA...



band_members

band_members %>% glimpse()
## Observations: 3
## Variables: 2
## $ name <chr> "Mick", "John", "Paul"
## $ band <chr> "Stones", "Beatles", "Beatles"



band_instruments

band_instruments %>% glimpse()
## Observations: 3
## Variables: 2
## $ name  <chr> "John", "Paul", "Keith"
## $ plays <chr> "guitar", "bass", "guitar"



band_instruments2

band_instruments2 %>% glimpse()
## Observations: 3
## Variables: 2
## $ artist <chr> "John", "Paul", "Keith"
## $ plays  <chr> "guitar", "bass", "guitar"



3 データフレーム操作

{tibble}関数群

概要

<概要>
・基本的な操作をパッケージ内で行うために以下の関数群がエクスポートされている



関数一覧

<関数一覧>
tibble        : モダンなデータフレームを作成
as_tibble     : モダンなデータフレームに変換
data_frame    : モダンなデータフレームを作成、tibble()のラッパー関数
as_data_frame : モダンなデータフレームに変換
add_row       : データフレームにレコードを追加
glimpse       : データセットの内容確認
frame_data  :
trunc_mat   :
type_sum      :
lst           : モダンなリストの作成  



{dplyr}関数群

add_rowname

概要

<概要>
・データフレームの行名を「列」として追加する
  - デフォルトでは"rowname"という列名
  - 列名は任意に指定できる
  

使用例

# 列名をデータフレームに追加
mtcars %>% add_rownames() %>% head(3)
## Warning: Deprecated, use tibble::rownames_to_column() instead.
## # A tibble: 3 x 12
##         rowname   mpg   cyl  disp    hp  drat    wt  qsec    vs    am
##           <chr> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl>
## 1     Mazda RX4  21.0     6   160   110  3.90 2.620 16.46     0     1
## 2 Mazda RX4 Wag  21.0     6   160   110  3.90 2.875 17.02     0     1
## 3    Datsun 710  22.8     4   108    93  3.85 2.320 18.61     1     1
## # ... with 2 more variables: gear <dbl>, carb <dbl>
# 列名を指定
mtcars %>% add_rownames("CarNames") %>% head(3)
## Warning: Deprecated, use tibble::rownames_to_column() instead.
## # A tibble: 3 x 12
##        CarNames   mpg   cyl  disp    hp  drat    wt  qsec    vs    am
##           <chr> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl> <dbl>
## 1     Mazda RX4  21.0     6   160   110  3.90 2.620 16.46     0     1
## 2 Mazda RX4 Wag  21.0     6   160   110  3.90 2.875 17.02     0     1
## 3    Datsun 710  22.8     4   108    93  3.85 2.320 18.61     1     1
## # ... with 2 more variables: gear <dbl>, carb <dbl>



参考:mtcarsデータセット

# 準備:「mtcars」は列名を持つデータフレーム
mtcars %>% attributes()
## $names
##  [1] "mpg"  "cyl"  "disp" "hp"   "drat" "wt"   "qsec" "vs"   "am"   "gear"
## [11] "carb"
## 
## $row.names
##  [1] "Mazda RX4"           "Mazda RX4 Wag"       "Datsun 710"         
##  [4] "Hornet 4 Drive"      "Hornet Sportabout"   "Valiant"            
##  [7] "Duster 360"          "Merc 240D"           "Merc 230"           
## [10] "Merc 280"            "Merc 280C"           "Merc 450SE"         
## [13] "Merc 450SL"          "Merc 450SLC"         "Cadillac Fleetwood" 
## [16] "Lincoln Continental" "Chrysler Imperial"   "Fiat 128"           
## [19] "Honda Civic"         "Toyota Corolla"      "Toyota Corona"      
## [22] "Dodge Challenger"    "AMC Javelin"         "Camaro Z28"         
## [25] "Pontiac Firebird"    "Fiat X1-9"           "Porsche 914-2"      
## [28] "Lotus Europa"        "Ford Pantera L"      "Ferrari Dino"       
## [31] "Maserati Bora"       "Volvo 142E"         
## 
## $class
## [1] "data.frame"



all_equal

概要

<概要>
・2つのデータセットが一致するかどうかを判定する
 - 一致する場合  :TRUE
  - 一致しない場合 :理由



使用例

iris6 %>% glimpse()
## Observations: 6
## Variables: 5
## $ Sepal.Length <dbl> 5.1, 4.9, 7.0, 6.4, 6.3, 5.8
## $ Sepal.Width  <dbl> 3.5, 3.0, 3.2, 3.2, 3.3, 2.7
## $ Petal.Length <dbl> 1.4, 1.4, 4.7, 4.5, 6.0, 5.1
## $ Petal.Width  <dbl> 0.2, 0.2, 1.4, 1.5, 2.5, 1.9
## $ Species      <fctr> setosa, setosa, versicolor, versicolor, virginic...
iris9 %>% glimpse()
## Observations: 9
## Variables: 5
## $ Sepal.Length <dbl> 5.1, 4.9, 4.7, 7.0, 6.4, 6.9, 6.3, 5.8, 7.1
## $ Sepal.Width  <dbl> 3.5, 3.0, 3.2, 3.2, 3.2, 3.1, 3.3, 2.7, 3.0
## $ Petal.Length <dbl> 1.4, 1.4, 1.3, 4.7, 4.5, 4.9, 6.0, 5.1, 5.9
## $ Petal.Width  <dbl> 0.2, 0.2, 0.2, 1.4, 1.5, 1.5, 2.5, 1.9, 2.1
## $ Species      <fctr> setosa, setosa, setosa, versicolor, versicolor, ...
# データセットが一致するかを判定
iris6 %>% all_equal(iris6)
## [1] TRUE
# データセットが一致するかを判定
iris6 %>% all_equal(iris9)
## [1] "Different number of rows"



tblクラス関数群

tbl

tbl_cube

tbl_df

tbl_sql

tbl_vars

as.tbl

as.tbl_cube

bench_tbls

compare_tbls

eval_tbls

is.tbl

make_tbl

src_tbls

4 基本操作

列の選択

全体像

<概要>
・指定した列を選択して新しいデータセットを作る
 - 指定の際に列名の変更も可能
 - 列選択を柔軟に行うためのサポート関数群がある


<関数一覧>
・select    :
・select_    :
・select_at  :
・select_all :
・select_if  :
・select_vars :
・pull      :


<列選択のサポート関数群>
・starts_with
・ends_with
・contains
・matches
・one_of
・everything
・num_range



select

概要

<概要>

- 「列の選択」には`select関数`を使い、以下の3つの方法で列選択をする
    - 列名を明示的に指定
    - 「:」を使用して範囲指定
    - 「-」を使用して除外
    
- 「列名の変更」は`select関数`と`rename関数`の両方で行うことができる
    - `select関数`は列選択を伴う
    - `rename関数`は全体のデータセットを選択したまま
    



使用例

<ポイント>
・列名を指定して選択する
# 列名を指定して選択
iris6 %>% select(Species, Sepal.Length, Sepal.Width)
## # A tibble: 6 x 3
##      Species Sepal.Length Sepal.Width
##       <fctr>        <dbl>       <dbl>
## 1     setosa          5.1         3.5
## 2     setosa          4.9         3.0
## 3 versicolor          7.0         3.2
## 4 versicolor          6.4         3.2
## 5  virginica          6.3         3.3
## 6  virginica          5.8         2.7



例1:範囲指定

<ポイント>
・列名を「:」でつなげることで範囲指定ができる
# フィールドを範囲指定する(:)
iris6 %>% select(Sepal.Length:Petal.Width)
## # A tibble: 6 x 4
##   Sepal.Length Sepal.Width Petal.Length Petal.Width
##          <dbl>       <dbl>        <dbl>       <dbl>
## 1          5.1         3.5          1.4         0.2
## 2          4.9         3.0          1.4         0.2
## 3          7.0         3.2          4.7         1.4
## 4          6.4         3.2          4.5         1.5
## 5          6.3         3.3          6.0         2.5
## 6          5.8         2.7          5.1         1.9
# 連続したフィールドを一旦取り出してから、特定フィールドを除去する
iris6 %>% select(Sepal.Length:Petal.Width, -(Petal.Length))
## # A tibble: 6 x 3
##   Sepal.Length Sepal.Width Petal.Width
##          <dbl>       <dbl>       <dbl>
## 1          5.1         3.5         0.2
## 2          4.9         3.0         0.2
## 3          7.0         3.2         1.4
## 4          6.4         3.2         1.5
## 5          6.3         3.3         2.5
## 6          5.8         2.7         1.9



例2:除去指定

<ポイント>
・列名に「-」を付けることで除外指定ができる
# 特定列を除外
iris6 %>% select(-Species)
## # A tibble: 6 x 4
##   Sepal.Length Sepal.Width Petal.Length Petal.Width
##          <dbl>       <dbl>        <dbl>       <dbl>
## 1          5.1         3.5          1.4         0.2
## 2          4.9         3.0          1.4         0.2
## 3          7.0         3.2          4.7         1.4
## 4          6.4         3.2          4.5         1.5
## 5          6.3         3.3          6.0         2.5
## 6          5.8         2.7          5.1         1.9
# 複数列を除外
iris6 %>% select(-Sepal.Length, -Species)
## # A tibble: 6 x 3
##   Sepal.Width Petal.Length Petal.Width
##         <dbl>        <dbl>       <dbl>
## 1         3.5          1.4         0.2
## 2         3.0          1.4         0.2
## 3         3.2          4.7         1.4
## 4         3.2          4.5         1.5
## 5         3.3          6.0         2.5
## 6         2.7          5.1         1.9
# 範囲指定の除外
iris6 %>% select(-(Sepal.Length:Petal.Width))
## # A tibble: 6 x 1
##      Species
##       <fctr>
## 1     setosa
## 2     setosa
## 3 versicolor
## 4 versicolor
## 5  virginica
## 6  virginica



例3:番号指定

<ポイント>
・列番号による列選択や列除外も可能
# 列指定
iris6 %>% select(5, 1, 2)
## # A tibble: 6 x 3
##      Species Sepal.Length Sepal.Width
##       <fctr>        <dbl>       <dbl>
## 1     setosa          5.1         3.5
## 2     setosa          4.9         3.0
## 3 versicolor          7.0         3.2
## 4 versicolor          6.4         3.2
## 5  virginica          6.3         3.3
## 6  virginica          5.8         2.7
# 列除外
iris6 %>% select(-5)
## # A tibble: 6 x 4
##   Sepal.Length Sepal.Width Petal.Length Petal.Width
##          <dbl>       <dbl>        <dbl>       <dbl>
## 1          5.1         3.5          1.4         0.2
## 2          4.9         3.0          1.4         0.2
## 3          7.0         3.2          4.7         1.4
## 4          6.4         3.2          4.5         1.5
## 5          6.3         3.3          6.0         2.5
## 6          5.8         2.7          5.1         1.9



select_

概要

<概要>

- select関数での列選択は文字列は受け付けない(非標準評価)
- select_関数では引数に文字列が使える(標準評価)
- 通常のdplyrの流れだと「非標準評価」を使うが、その他の場合は「標準評価」を使うこともある
- エラー原因になりやすいので注意する



標準評価

# select関数の引数を文字列にする(非標準評価)
# --- エラーになる
iris %>% 
  select("Sepal.Length", "Sepal.Width") %>% 
  head()
##   Sepal.Length Sepal.Width
## 1          5.1         3.5
## 2          4.9         3.0
## 3          4.7         3.2
## 4          4.6         3.1
## 5          5.0         3.6
## 6          5.4         3.9
# select_関数の引数を文字列を使える(標準評価)
iris %>% 
  select_("Sepal.Length", "Sepal.Width") %>% 
  head()
##   Sepal.Length Sepal.Width
## 1          5.1         3.5
## 2          4.9         3.0
## 3          4.7         3.2
## 4          4.6         3.1
## 5          5.0         3.6
## 6          5.4         3.9



非標準評価

# select関数の引数を文字列にする(非標準評価)
# --- エラーになる
iris %>% 
  select(Sepal.Length, Sepal.Width) %>% 
  head()
##   Sepal.Length Sepal.Width
## 1          5.1         3.5
## 2          4.9         3.0
## 3          4.7         3.2
## 4          4.6         3.1
## 5          5.0         3.6
## 6          5.4         3.9



列選択のサポート関数群

概要

<ポイント>
・select関数ではサポート関数を用いたフィールド抽出が可能


<サポート関数一覧>
前方一致   : starts_with()
後方一致   : ends_with()
部分一致  : contains()
正規表現   : matches()
列名リスト : one_of()
全体選択  : everything()
連番範囲  : num_range()

starts_with

<ポイント>
・前方一致で列を選択
# 前方一致
iris6 %>% select(starts_with("sepal"))
## # A tibble: 6 x 2
##   Sepal.Length Sepal.Width
##          <dbl>       <dbl>
## 1          5.1         3.5
## 2          4.9         3.0
## 3          7.0         3.2
## 4          6.4         3.2
## 5          6.3         3.3
## 6          5.8         2.7



ends_with

<ポイント>
・後方一致で列を選択
# 後方一致
iris6 %>% select(ends_with("width"))
## # A tibble: 6 x 2
##   Sepal.Width Petal.Width
##         <dbl>       <dbl>
## 1         3.5         0.2
## 2         3.0         0.2
## 3         3.2         1.4
## 4         3.2         1.5
## 5         3.3         2.5
## 6         2.7         1.9



contains

<ポイント>
・部分一致で列を選択
# 部分一致
iris6 %>% select(contains("pe"))
## # A tibble: 6 x 3
##   Petal.Length Petal.Width    Species
##          <dbl>       <dbl>     <fctr>
## 1          1.4         0.2     setosa
## 2          1.4         0.2     setosa
## 3          4.7         1.4 versicolor
## 4          4.5         1.5 versicolor
## 5          6.0         2.5  virginica
## 6          5.1         1.9  virginica



matches

<ポイント>
・正規表現で列を選択
# 正規表現
iris6 %>% select(matches(".t."))
## # A tibble: 6 x 4
##   Sepal.Length Sepal.Width Petal.Length Petal.Width
##          <dbl>       <dbl>        <dbl>       <dbl>
## 1          5.1         3.5          1.4         0.2
## 2          4.9         3.0          1.4         0.2
## 3          7.0         3.2          4.7         1.4
## 4          6.4         3.2          4.5         1.5
## 5          6.3         3.3          6.0         2.5
## 6          5.8         2.7          5.1         1.9



one_of

<ポイント>
・列名リスト選択で列を選択
# 列名リスト選択
iris6 %>% select(one_of(c("Sepal.Length", "Species")))
## # A tibble: 6 x 2
##   Sepal.Length    Species
##          <dbl>     <fctr>
## 1          5.1     setosa
## 2          4.9     setosa
## 3          7.0 versicolor
## 4          6.4 versicolor
## 5          6.3  virginica
## 6          5.8  virginica



everything

<ポイント>
・既出の列を除く全ての列を選択
# 既出のものを除く全てのフィールド(応用2を確認)
iris6 %>% select(everything())
## # A tibble: 6 x 5
##   Sepal.Length Sepal.Width Petal.Length Petal.Width    Species
##          <dbl>       <dbl>        <dbl>       <dbl>     <fctr>
## 1          5.1         3.5          1.4         0.2     setosa
## 2          4.9         3.0          1.4         0.2     setosa
## 3          7.0         3.2          4.7         1.4 versicolor
## 4          6.4         3.2          4.5         1.5 versicolor
## 5          6.3         3.3          6.0         2.5  virginica
## 6          5.8         2.7          5.1         1.9  virginica
# 特定の列を1番目にして、あとは同じ並び方
iris6 %>% select(Species, everything()) 
## # A tibble: 6 x 5
##      Species Sepal.Length Sepal.Width Petal.Length Petal.Width
##       <fctr>        <dbl>       <dbl>        <dbl>       <dbl>
## 1     setosa          5.1         3.5          1.4         0.2
## 2     setosa          4.9         3.0          1.4         0.2
## 3 versicolor          7.0         3.2          4.7         1.4
## 4 versicolor          6.4         3.2          4.5         1.5
## 5  virginica          6.3         3.3          6.0         2.5
## 6  virginica          5.8         2.7          5.1         1.9



num_range

<ポイント>
・



select_at

概要

使用例

select_all

概要

使用例

select_if

概要

<概要>
・特定の条件の列のみを選択する場合に使用する
 - 特定の条件はTRUE/FALSEを返す関数(叙述関数)で表現する 
 - 「is.numeric」など
 

<使用イメージ>
- 特定のデータ型の列のみを選択
- 平均が指定値を超える列
    



例1:is関数群による選択

# 数字型の列のみを抽出
iris6 %>% select_if(is.numeric)
## # A tibble: 6 x 4
##   Sepal.Length Sepal.Width Petal.Length Petal.Width
##          <dbl>       <dbl>        <dbl>       <dbl>
## 1          5.1         3.5          1.4         0.2
## 2          4.9         3.0          1.4         0.2
## 3          7.0         3.2          4.7         1.4
## 4          6.4         3.2          4.5         1.5
## 5          6.3         3.3          6.0         2.5
## 6          5.8         2.7          5.1         1.9
# ファクター(文字列)の列のみを抽出
iris6 %>% select_if(is.factor)
## # A tibble: 6 x 1
##      Species
##       <fctr>
## 1     setosa
## 2     setosa
## 3 versicolor
## 4 versicolor
## 5  virginica
## 6  virginica



例2:無名関数による定義

# 条件関数を無名関数で作成
# --- 平均が3.5を超える数値列を取得
iris6 %>% select_if(function(col) is.numeric(col) == TRUE && mean(col) > 3)
## # A tibble: 6 x 3
##   Sepal.Length Sepal.Width Petal.Length
##          <dbl>       <dbl>        <dbl>
## 1          5.1         3.5          1.4
## 2          4.9         3.0          1.4
## 3          7.0         3.2          4.7
## 4          6.4         3.2          4.5
## 5          6.3         3.3          6.0
## 6          5.8         2.7          5.1
# 参考:関数の出力結果
iris6 %>% sapply(function(col) is.numeric(col) == TRUE && mean(col) > 3)
## Sepal.Length  Sepal.Width Petal.Length  Petal.Width      Species 
##         TRUE         TRUE         TRUE        FALSE        FALSE



select_vars

概要

<概要>
・列名ベクトルから、指定した条件の列名のみを取得
 - names()でデータフレームから予め列名ベクトルを取得しておく
    



使用例

# 全ての列の列名を選択
iris %>% names() %>% select_vars(everything())
##   Sepal.Length    Sepal.Width   Petal.Length    Petal.Width        Species 
## "Sepal.Length"  "Sepal.Width" "Petal.Length"  "Petal.Width"      "Species"
# 列が「Petal」で始まる
iris %>% names() %>% select_vars(starts_with("Petal"))
##   Petal.Length    Petal.Width 
## "Petal.Length"  "Petal.Width"



参考:names()

# データセットの列名を取得
iris %>% names() 
## [1] "Sepal.Length" "Sepal.Width"  "Petal.Length" "Petal.Width" 
## [5] "Species"



pull

概要

<概要>
・データフレームの指定列をベクトル形式で抽出する
 - 通常のデータフレームの場合は演算子などでも対応可能
 - {dbplyr}のデータベース操作にも対応


<類似操作>
・[[]]演算子
・magrittr::extract()



使用例

# 指定列をベクトルで出力
iris6 %>% pull(Sepal.Length)
## [1] 5.1 4.9 7.0 6.4 6.3 5.8
# 別解1:[[]]演算子
iris6[["Sepal.Length"]]
## [1] 5.1 4.9 7.0 6.4 6.3 5.8
# 別解3:extract2
iris6 %>% magrittr::extract2("Sepal.Length")
## [1] 5.1 4.9 7.0 6.4 6.3 5.8



dbplyr

X <- dbplyr::memdb_frame(1:3) %T>% print()
## # Source:   table<waqiwcuqjl> [?? x 1]
## # Database: sqlite 3.11.1 [:memory:]
##   `1:3`
##   <int>
## 1     1
## 2     2
## 3     3
X  %>% pull(1)
## [1] 1 2 3

列名の変更

全体像

<概要>
・元のデータセットの指定した列の名前を変更する
 - 既存のデータセットは維持される


<関数一覧>
・rename    :
・rename_all :
・rename_at  :
・rename_if  :
・rename_vars :



rename

概要

<ポイント>

- 「列名の変更」は`select関数`と`rename関数`の両方で行うことができる
    - `select関数`は列選択を伴う
    - `rename関数`は全体のデータセットを選択したまま
    



使用例

<ポイント>
・元のデータセットが選択されたままで列名のみが変更されている
iris6 %>% rename(SL = Sepal.Length, 
                 SW = Sepal.Width)
## # A tibble: 6 x 5
##      SL    SW Petal.Length Petal.Width    Species
##   <dbl> <dbl>        <dbl>       <dbl>     <fctr>
## 1   5.1   3.5          1.4         0.2     setosa
## 2   4.9   3.0          1.4         0.2     setosa
## 3   7.0   3.2          4.7         1.4 versicolor
## 4   6.4   3.2          4.5         1.5 versicolor
## 5   6.3   3.3          6.0         2.5  virginica
## 6   5.8   2.7          5.1         1.9  virginica



例:select()による列名変更

<ポイント>
・指定した列のみ列名のみが変更されて選択される
iris6 %>% select(SL = Sepal.Length, 
                 SW = Sepal.Width)
## # A tibble: 6 x 2
##      SL    SW
##   <dbl> <dbl>
## 1   5.1   3.5
## 2   4.9   3.0
## 3   7.0   3.2
## 4   6.4   3.2
## 5   6.3   3.3
## 6   5.8   2.7



rename_at

rename_all

rename_if

rename_vars

概要

使用例

rename_vars(names(iris), petal_length = Petal.Length)
##   Sepal.Length    Sepal.Width   petal_length    Petal.Width        Species 
## "Sepal.Length"  "Sepal.Width" "Petal.Length"  "Petal.Width"      "Species"



列の追加

全体像

<概要>
・元のデータセットの指定した列の名前を変更する
 - 既存のデータセットは維持される


<関数一覧>
・mutate        :
・mutate_all     :
・mutate_at      :
・mutate_if      :
・transmutate    :
・transmutate_all :
・transmutate_at :
・transmutate_if :



mutate

概要

<概要>
・データセットの最後に定義に基づいた列を追加する
・列名を同じにすると、既存の列を上書きする



使用例

# 列を追加
iris6 %>% 
  mutate(mean_SL  = mean(Sepal.Length))
## # A tibble: 6 x 6
##   Sepal.Length Sepal.Width Petal.Length Petal.Width    Species  mean_SL
##          <dbl>       <dbl>        <dbl>       <dbl>     <fctr>    <dbl>
## 1          5.1         3.5          1.4         0.2     setosa 5.916667
## 2          4.9         3.0          1.4         0.2     setosa 5.916667
## 3          7.0         3.2          4.7         1.4 versicolor 5.916667
## 4          6.4         3.2          4.5         1.5 versicolor 5.916667
## 5          6.3         3.3          6.0         2.5  virginica 5.916667
## 6          5.8         2.7          5.1         1.9  virginica 5.916667
# 既存の列を上書き
iris6 %>% 
  mutate(Sepal.Length  = mean(Sepal.Length))
## # A tibble: 6 x 5
##   Sepal.Length Sepal.Width Petal.Length Petal.Width    Species
##          <dbl>       <dbl>        <dbl>       <dbl>     <fctr>
## 1     5.916667         3.5          1.4         0.2     setosa
## 2     5.916667         3.0          1.4         0.2     setosa
## 3     5.916667         3.2          4.7         1.4 versicolor
## 4     5.916667         3.2          4.5         1.5 versicolor
## 5     5.916667         3.3          6.0         2.5  virginica
## 6     5.916667         2.7          5.1         1.9  virginica



mutate_all

概要

<概要>
・全ての列に指定した関数を適用する
  - funs()の中に適用したい関数を入力する
  - 複数の関数を入力することもできる


<類似関数>
・purrrlyr::dmap()



使用例

# 全ての列を平均に変換する
iris6[, 1:4] %>% 
  mutate_all(funs(mean))
## # A tibble: 6 x 4
##   Sepal.Length Sepal.Width Petal.Length Petal.Width
##          <dbl>       <dbl>        <dbl>       <dbl>
## 1     5.916667        3.15         3.85    1.283333
## 2     5.916667        3.15         3.85    1.283333
## 3     5.916667        3.15         3.85    1.283333
## 4     5.916667        3.15         3.85    1.283333
## 5     5.916667        3.15         3.85    1.283333
## 6     5.916667        3.15         3.85    1.283333
# 既存の列を上書き
iris6[, 1] %>% 
  mutate_all(funs(mean, cumsum))
## Warning: package 'bindrcpp' was built under R version 3.3.3
## # A tibble: 6 x 3
##   Sepal.Length     mean cumsum
##          <dbl>    <dbl>  <dbl>
## 1          5.1 5.916667    5.1
## 2          4.9 5.916667   10.0
## 3          7.0 5.916667   17.0
## 4          6.4 5.916667   23.4
## 5          6.3 5.916667   29.7
## 6          5.8 5.916667   35.5



mutate_at

概要

<概要>
・
  
列選択のサポート関数群

使用例

<ポイント>
- すべての列に対して指定した複数関数を適用して列を作成することができる
- mutate_allの箇所で集計するので、group_byによるグループ化が必要
iris %>% 
  select(Species, Sepal.Length, Sepal.Width) %>% 
  group_by(Species) %>% 
  mutate_at(vars(ends_with("Length")), funs(min, max)) %>% {
    head(.) %>% print()
    str(.) %>% print()
  }
## # A tibble: 6 x 5
## # Groups:   Species [1]
##   Species Sepal.Length Sepal.Width   min   max
##    <fctr>        <dbl>       <dbl> <dbl> <dbl>
## 1  setosa          5.1         3.5   4.3   5.8
## 2  setosa          4.9         3.0   4.3   5.8
## 3  setosa          4.7         3.2   4.3   5.8
## 4  setosa          4.6         3.1   4.3   5.8
## 5  setosa          5.0         3.6   4.3   5.8
## 6  setosa          5.4         3.9   4.3   5.8
## Classes 'grouped_df', 'tbl_df', 'tbl' and 'data.frame':  150 obs. of  5 variables:
##  $ Species     : Factor w/ 3 levels "setosa","versicolor",..: 1 1 1 1 1 1 1 1 1 1 ...
##  $ Sepal.Length: num  5.1 4.9 4.7 4.6 5 5.4 4.6 5 4.4 4.9 ...
##  $ Sepal.Width : num  3.5 3 3.2 3.1 3.6 3.9 3.4 3.4 2.9 3.1 ...
##  $ min         : num  4.3 4.3 4.3 4.3 4.3 4.3 4.3 4.3 4.3 4.3 ...
##  $ max         : num  5.8 5.8 5.8 5.8 5.8 5.8 5.8 5.8 5.8 5.8 ...
##  - attr(*, "vars")= chr "Species"
##  - attr(*, "labels")='data.frame':   3 obs. of  1 variable:
##   ..$ Species: Factor w/ 3 levels "setosa","versicolor",..: 1 2 3
##   ..- attr(*, "vars")= chr "Species"
##   ..- attr(*, "drop")= logi TRUE
##  - attr(*, "indices")=List of 3
##   ..$ : int  0 1 2 3 4 5 6 7 8 9 ...
##   ..$ : int  50 51 52 53 54 55 56 57 58 59 ...
##   ..$ : int  100 101 102 103 104 105 106 107 108 109 ...
##  - attr(*, "drop")= logi TRUE
##  - attr(*, "group_sizes")= int  50 50 50
##  - attr(*, "biggest_group_size")= int 50
## NULL



mutate_if

概要

使用例

<ポイント>
- 条件に適合する列に対して指定した複数関数を適用して列を作成することができる
- 第1引数の関数にはカッコ()を付けない、is.numeric()ではない
iris %>% 
  select(Species, Sepal.Length, Sepal.Width) %>% 
  mutate(Sepal.Length_Cha = as.character(Sepal.Length)) %>% 
  group_by(Species) %>% 
  mutate_if(is.numeric, funs(min, max)) %>% 
  head
## # A tibble: 6 x 8
## # Groups:   Species [1]
##   Species Sepal.Length Sepal.Width Sepal.Length_Cha Sepal.Length_min
##    <fctr>        <dbl>       <dbl>            <chr>            <dbl>
## 1  setosa          5.1         3.5              5.1              4.3
## 2  setosa          4.9         3.0              4.9              4.3
## 3  setosa          4.7         3.2              4.7              4.3
## 4  setosa          4.6         3.1              4.6              4.3
## 5  setosa          5.0         3.6                5              4.3
## 6  setosa          5.4         3.9              5.4              4.3
## # ... with 3 more variables: Sepal.Width_min <dbl>,
## #   Sepal.Length_max <dbl>, Sepal.Width_max <dbl>



transmute

概要

<概要>
・新しい列を定義して、新しいデータセットとして追加する
  - 既存のデータフレームの情報は引き継がれない


<類似操作>
・mutate



使用例

# 集計列のみを出力
iris6 %>% 
  transmute(diff = Sepal.Length - Petal.Length)
## # A tibble: 6 x 1
##    diff
##   <dbl>
## 1   3.7
## 2   3.5
## 3   2.3
## 4   1.9
## 5   0.3
## 6   0.7
# 参考:計算証明
iris6 %>% 
  select(Sepal.Length, Petal.Length) %>% 
  mutate(diff = Sepal.Length - Petal.Length)
## # A tibble: 6 x 3
##   Sepal.Length Petal.Length  diff
##          <dbl>        <dbl> <dbl>
## 1          5.1          1.4   3.7
## 2          4.9          1.4   3.5
## 3          7.0          4.7   2.3
## 4          6.4          4.5   1.9
## 5          6.3          6.0   0.3
## 6          5.8          5.1   0.7



transmute_all

概要

使用例

transmute_all
## function (.tbl, .funs, ...) 
## {
##     funs <- manip_all(.tbl, .funs, enquo(.funs), caller_env(), 
##         ...)
##     transmute(.tbl, !(!(!funs)))
## }
## <environment: namespace:dplyr>

transmute_at

概要

使用例

transmute_if

概要

使用例

レコード抽出

全体像

<概要>
- 「レコードの抽出」は`filter関数`と`slice関数`と`top_n関数`で行うことができる
    - `filter関数`は指定条件に基づいてレコード抽出
    - `slice関数`は番号指定でレコード抽出
    - `top_n関数`はランキングに基づいて抽出


<関数一覧>
・filter    :
・filter_all :
・filter_at  :
・filter_if  :
・slice     :
・top_n    :
・sample_n  :
・sample_frac :


<注意事項>
・filter関数は{base}と競合するので注意が必要
 - dplyr::filter()と明示
 - needs::priortize()で優先順位のコントロール



filter

概要

例1:単一条件

<ポイント>
・一致条件は「==」で表現する
  - 「=」ではないので注意
# 1つの条件で抽出
iris9 %>% dplyr::filter(Species == "setosa")
## # A tibble: 3 x 5
##   Sepal.Length Sepal.Width Petal.Length Petal.Width Species
##          <dbl>       <dbl>        <dbl>       <dbl>  <fctr>
## 1          5.1         3.5          1.4         0.2  setosa
## 2          4.9         3.0          1.4         0.2  setosa
## 3          4.7         3.2          1.3         0.2  setosa



例2:AND条件

<ポイント>
・AND条件は「,(カンマ)」でつなぐ
  - 「AND」ではないので注意
# 2つの条件をANDで抽出
iris9 %>% dplyr::filter(Species == "setosa", Sepal.Length < 5)
## # A tibble: 2 x 5
##   Sepal.Length Sepal.Width Petal.Length Petal.Width Species
##          <dbl>       <dbl>        <dbl>       <dbl>  <fctr>
## 1          4.9         3.0          1.4         0.2  setosa
## 2          4.7         3.2          1.3         0.2  setosa



例3:OR条件

<ポイント>
・OR条件は「||」でつなぐ
  - 「OR」ではないので注意
# 2つの条件をANDで抽出
iris9 %>% dplyr::filter(Species == "setosa" || Sepal.Length < 5)
## # A tibble: 9 x 5
##   Sepal.Length Sepal.Width Petal.Length Petal.Width    Species
##          <dbl>       <dbl>        <dbl>       <dbl>     <fctr>
## 1          5.1         3.5          1.4         0.2     setosa
## 2          4.9         3.0          1.4         0.2     setosa
## 3          4.7         3.2          1.3         0.2     setosa
## 4          7.0         3.2          4.7         1.4 versicolor
## 5          6.4         3.2          4.5         1.5 versicolor
## 6          6.9         3.1          4.9         1.5 versicolor
## 7          6.3         3.3          6.0         2.5  virginica
## 8          5.8         2.7          5.1         1.9  virginica
## 9          7.1         3.0          5.9         2.1  virginica



例4:NOT条件

<ポイント>
・NOT条件は「!」で全体を括る
# 2つの条件をANDで抽出
iris9 %>% dplyr::filter(!(Species == "setosa"))
## # A tibble: 6 x 5
##   Sepal.Length Sepal.Width Petal.Length Petal.Width    Species
##          <dbl>       <dbl>        <dbl>       <dbl>     <fctr>
## 1          7.0         3.2          4.7         1.4 versicolor
## 2          6.4         3.2          4.5         1.5 versicolor
## 3          6.9         3.1          4.9         1.5 versicolor
## 4          6.3         3.3          6.0         2.5  virginica
## 5          5.8         2.7          5.1         1.9  virginica
## 6          7.1         3.0          5.9         2.1  virginica



filter_all

filter_at

filter_if

slice

概要

<概要>
・指定したレコード番号を抽出する



使用例

# 1-2番目を抽出
iris6 %>% slice(1:2)
## # A tibble: 2 x 5
##   Sepal.Length Sepal.Width Petal.Length Petal.Width Species
##          <dbl>       <dbl>        <dbl>       <dbl>  <fctr>
## 1          5.1         3.5          1.4         0.2  setosa
## 2          4.9         3.0          1.4         0.2  setosa
# 2-3番目を抽出
iris6 %>% slice(2:3)
## # A tibble: 2 x 5
##   Sepal.Length Sepal.Width Petal.Length Petal.Width    Species
##          <dbl>       <dbl>        <dbl>       <dbl>     <fctr>
## 1          4.9         3.0          1.4         0.2     setosa
## 2          7.0         3.2          4.7         1.4 versicolor
# 1,3,5番目を抽出
iris6 %>% slice(c(1, 3, 5))
## # A tibble: 3 x 5
##   Sepal.Length Sepal.Width Petal.Length Petal.Width    Species
##          <dbl>       <dbl>        <dbl>       <dbl>     <fctr>
## 1          5.1         3.5          1.4         0.2     setosa
## 2          7.0         3.2          4.7         1.4 versicolor
## 3          6.3         3.3          6.0         2.5  virginica



top_n

概要

使用例

iris6 %>% top_n(3)
## Selecting by Species
## # A tibble: 4 x 5
##   Sepal.Length Sepal.Width Petal.Length Petal.Width    Species
##          <dbl>       <dbl>        <dbl>       <dbl>     <fctr>
## 1          7.0         3.2          4.7         1.4 versicolor
## 2          6.4         3.2          4.5         1.5 versicolor
## 3          6.3         3.3          6.0         2.5  virginica
## 4          5.8         2.7          5.1         1.9  virginica

sample_n

概要

<概要>
・データフレームから指定した数のレコードをランダムに取得する



使用例

# データフレームから指定した数のレコードをランダムに取得
iris9 %>% sample_n(3)
## # A tibble: 3 x 5
##   Sepal.Length Sepal.Width Petal.Length Petal.Width    Species
##          <dbl>       <dbl>        <dbl>       <dbl>     <fctr>
## 1          4.7         3.2          1.3         0.2     setosa
## 2          5.1         3.5          1.4         0.2     setosa
## 3          7.0         3.2          4.7         1.4 versicolor



sample_frac

概要

<概要>
・データフレームの全レコード数から指定パーセントのレコードをランダムに抽出する



使用例

# データフレームの全レコード数から指定パーセントのレコードをランダムに抽出
iris %>% as_tibble() %>% sample_frac(0.1)
## # A tibble: 15 x 5
##    Sepal.Length Sepal.Width Petal.Length Petal.Width    Species
##           <dbl>       <dbl>        <dbl>       <dbl>     <fctr>
##  1          5.6         2.9          3.6         1.3 versicolor
##  2          5.7         2.9          4.2         1.3 versicolor
##  3          5.2         4.1          1.5         0.1     setosa
##  4          7.1         3.0          5.9         2.1  virginica
##  5          6.7         2.5          5.8         1.8  virginica
##  6          5.1         2.5          3.0         1.1 versicolor
##  7          6.3         2.9          5.6         1.8  virginica
##  8          6.3         2.5          5.0         1.9  virginica
##  9          5.8         4.0          1.2         0.2     setosa
## 10          7.3         2.9          6.3         1.8  virginica
## 11          5.1         3.4          1.5         0.2     setosa
## 12          6.3         2.5          4.9         1.5 versicolor
## 13          6.7         3.3          5.7         2.1  virginica
## 14          6.3         2.3          4.4         1.3 versicolor
## 15          5.9         3.0          5.1         1.8  virginica



レコード並び替え

全体像

<概要>
・データフレームのレコードの並び替えを行う


<関数一覧>
・arrange    :
・arrange_all :
・arrange_at  :
・arrange_if  :
・desc     :並び順を降順に変換する(要素に-1を乗じる)
・order_by   :



arrange

概要

<概要>
・レコードを指定した列を基準に並び替える
  - デフォルトの並び順は昇順
  - 降順にする場合はdesc関数を用いる
  
・グループ内での集計も可能
 - .by_group引数をTRUEにする



例1:昇順

# 2つのキーを全て昇順
iris6 %>% 
  select(Sepal.Width, Sepal.Length) %>% 
  arrange(Sepal.Width, Sepal.Length)
## # A tibble: 6 x 2
##   Sepal.Width Sepal.Length
##         <dbl>        <dbl>
## 1         2.7          5.8
## 2         3.0          4.9
## 3         3.2          6.4
## 4         3.2          7.0
## 5         3.3          6.3
## 6         3.5          5.1



例2:降順

# 2つのキーを昇順と降順
iris6 %>% 
  select(Sepal.Width, Sepal.Length) %>% 
  arrange(Sepal.Width, desc(Sepal.Length))
## # A tibble: 6 x 2
##   Sepal.Width Sepal.Length
##         <dbl>        <dbl>
## 1         2.7          5.8
## 2         3.0          4.9
## 3         3.2          7.0
## 4         3.2          6.4
## 5         3.3          6.3
## 6         3.5          5.1
# 2つを降順にする場合
iris6 %>% 
  select(Sepal.Width, Sepal.Length) %>% 
  arrange(desc(Sepal.Width, Sepal.Length))
## # A tibble: 6 x 2
##   Sepal.Width Sepal.Length
##         <dbl>        <dbl>
## 1         3.5          5.1
## 2         3.3          6.3
## 3         3.2          7.0
## 4         3.2          6.4
## 5         3.0          4.9
## 6         2.7          5.8



例3:グループ単位の並び替え

# グループ内での並び替え
iris9 %>% 
  select(Species, Sepal.Length) %>% 
  group_by(Species) %>% 
  arrange(Sepal.Length, .by_group = TRUE)
## # A tibble: 9 x 2
## # Groups:   Species [3]
##      Species Sepal.Length
##       <fctr>        <dbl>
## 1     setosa          4.7
## 2     setosa          4.9
## 3     setosa          5.1
## 4 versicolor          6.4
## 5 versicolor          6.9
## 6 versicolor          7.0
## 7  virginica          5.8
## 8  virginica          6.3
## 9  virginica          7.1
# グループに関係なく並び替え
# --- 初期設定はFALSE
iris9 %>% 
  select(Species, Sepal.Length) %>% 
  group_by(Species) %>% 
  arrange(Sepal.Length)
## # A tibble: 9 x 2
## # Groups:   Species [3]
##      Species Sepal.Length
##       <fctr>        <dbl>
## 1     setosa          4.7
## 2     setosa          4.9
## 3     setosa          5.1
## 4  virginica          5.8
## 5  virginica          6.3
## 6 versicolor          6.4
## 7 versicolor          6.9
## 8 versicolor          7.0
## 9  virginica          7.1



arrange_all

arrange_at

arrange_if

desc

概要

<概要>
・並び順を降順に変換する(要素に-1を乗じる)
 - NAはそのまま
  

<活用シーン>
・レコード並び替え:arrange()
・ランキング   :row_number()



使用例

# descは元の値に-1を乗じる
c(1:5, NA) %>% desc()
## [1] -1 -2 -3 -4 -5 NA
# 降順とdesc()の関係
iris6 %>% 
  select(Sepal.Length) %>% 
  mutate(desc = desc(Sepal.Length)) %>% 
  arrange(desc(Sepal.Length))
## # A tibble: 6 x 2
##   Sepal.Length  desc
##          <dbl> <dbl>
## 1          7.0  -7.0
## 2          6.4  -6.4
## 3          6.3  -6.3
## 4          5.8  -5.8
## 5          5.1  -5.1
## 6          4.9  -4.9



order_by

order_by(10:1, cumsum(1:10))
##  [1] 55 54 52 49 45 40 34 27 19 10
x <- 10:1
y <- 1:10
order_by(x, cumsum(y))
##  [1] 55 54 52 49 45 40 34 27 19 10

概要

使用例

レコード重複排除

全体像

<概要>
・データフレームのレコードの重複排除


<関数一覧>
・distinct   :特定フィールドのレコードを一意にして取得
・n_distinct :データセットの要素を一意に集約した際の要素数を取得



distinct

概要

<概要>
・特定フィールドのレコードを一意にして取得
 - フィールドは複数指定することも可能
 
・データフレームの列に適用することを想定する
 - ベクトルには適用できない



使用例

# 単一列の一意化
iris6 %>% select(Species) %>% distinct()
## # A tibble: 3 x 1
##      Species
##       <fctr>
## 1     setosa
## 2 versicolor
## 3  virginica
# 複数列の一意化
flights %>% select(year, month) %>% distinct()
## # A tibble: 12 x 2
##     year month
##    <int> <int>
##  1  2013     1
##  2  2013    10
##  3  2013    11
##  4  2013    12
##  5  2013     2
##  6  2013     3
##  7  2013     4
##  8  2013     5
##  9  2013     6
## 10  2013     7
## 11  2013     8
## 12  2013     9



n_distinct

概要

<概要>
・データセットの要素を一意に集約した際の要素数を取得
 - ベクトルに対して適用できる、データフレームにも適用可能



使用例

# 準備:ベクトルの作成
set.seed(110)
X <- sample(1:10, 10, replace = TRUE) %>% sort() %T>% print()
##  [1]  2  3  6  7  7  8  8 10 10 10
# 重複排除した要素数
X %>% n_distinct()
## [1] 6



応用:データフレームへの適用

# 指定列の重複数
iris6 %>% n_distinct("Species")
## [1] 6
# 指定列の重複数
# --- n_distinct()を使わずに記述
iris6 %>% distinct(Sepal.Length) %>% as_vector() %>% length()
## [1] 6
# 列ごとの重複数
iris6 %>% mutate_all(funs(n_distinct))
## # A tibble: 6 x 5
##   Sepal.Length Sepal.Width Petal.Length Petal.Width Species
##          <int>       <int>        <int>       <int>   <int>
## 1            6           5            5           5       3
## 2            6           5            5           5       3
## 3            6           5            5           5       3
## 4            6           5            5           5       3
## 5            6           5            5           5       3
## 6            6           5            5           5       3



グループ化

全体像

<概要>
・データフレームを指定した列をキーにグループ化する
 - グループ設定はデータセットにグループ情報を与えるだけで表面的な変化はない


<関数一覧>
・group_by      :
・group_by_all   :
・group_by_at    :
・group_by_if    :
・group_by_prepare :並び順を降順に変換する(要素に-1を乗じる)
・ungroup      :
・rowwise      :



group_by

概要

<概要>
・データフレームを特定列でグループ化する
  - グループ単位での処理関数が適用できるようになる
  - データフレームに表面的な変化はない

例1:1段階グループ化

# グループ化はデータセット自体に変化はない
# --- クラス情報を持つ (Groups: Species [3])
iris6 %>% group_by(Species)
## # A tibble: 6 x 5
## # Groups:   Species [3]
##   Sepal.Length Sepal.Width Petal.Length Petal.Width    Species
##          <dbl>       <dbl>        <dbl>       <dbl>     <fctr>
## 1          5.1         3.5          1.4         0.2     setosa
## 2          4.9         3.0          1.4         0.2     setosa
## 3          7.0         3.2          4.7         1.4 versicolor
## 4          6.4         3.2          4.5         1.5 versicolor
## 5          6.3         3.3          6.0         2.5  virginica
## 6          5.8         2.7          5.1         1.9  virginica



例2:多段階グループ化

# 3列でグループ化
flights %>% select(year, month, day) %>% group_by(year, month, day)
## # A tibble: 336,776 x 3
## # Groups:   year, month, day [365]
##     year month   day
##    <int> <int> <int>
##  1  2013     1     1
##  2  2013     1     1
##  3  2013     1     1
##  4  2013     1     1
##  5  2013     1     1
##  6  2013     1     1
##  7  2013     1     1
##  8  2013     1     1
##  9  2013     1     1
## 10  2013     1     1
## # ... with 336,766 more rows



group_by_all

group_by_at

group_by_if

group_by_prepare

ungroup

概要

<概要>
・全てのグループ化情報を解除する
  - 多段階のグループ化も一度に解除できる



例1:1段階グループ化

# 準備:グループ化したデータフレームを作成
X <- iris6 %>% group_by(Species) %T>% print()
## # A tibble: 6 x 5
## # Groups:   Species [3]
##   Sepal.Length Sepal.Width Petal.Length Petal.Width    Species
##          <dbl>       <dbl>        <dbl>       <dbl>     <fctr>
## 1          5.1         3.5          1.4         0.2     setosa
## 2          4.9         3.0          1.4         0.2     setosa
## 3          7.0         3.2          4.7         1.4 versicolor
## 4          6.4         3.2          4.5         1.5 versicolor
## 5          6.3         3.3          6.0         2.5  virginica
## 6          5.8         2.7          5.1         1.9  virginica
# グループ化を解除
X %>% ungroup()
## # A tibble: 6 x 5
##   Sepal.Length Sepal.Width Petal.Length Petal.Width    Species
##          <dbl>       <dbl>        <dbl>       <dbl>     <fctr>
## 1          5.1         3.5          1.4         0.2     setosa
## 2          4.9         3.0          1.4         0.2     setosa
## 3          7.0         3.2          4.7         1.4 versicolor
## 4          6.4         3.2          4.5         1.5 versicolor
## 5          6.3         3.3          6.0         2.5  virginica
## 6          5.8         2.7          5.1         1.9  virginica



例2:多段階グループ化

# 準備:グループ化したデータフレームを作成
X <- flights %>% select(year, month, day) %>% group_by(year, month, day) %>% print()
## # A tibble: 336,776 x 3
## # Groups:   year, month, day [365]
##     year month   day
##    <int> <int> <int>
##  1  2013     1     1
##  2  2013     1     1
##  3  2013     1     1
##  4  2013     1     1
##  5  2013     1     1
##  6  2013     1     1
##  7  2013     1     1
##  8  2013     1     1
##  9  2013     1     1
## 10  2013     1     1
## # ... with 336,766 more rows
# グループ化を解除
X %>% ungroup()
## # A tibble: 336,776 x 3
##     year month   day
##    <int> <int> <int>
##  1  2013     1     1
##  2  2013     1     1
##  3  2013     1     1
##  4  2013     1     1
##  5  2013     1     1
##  6  2013     1     1
##  7  2013     1     1
##  8  2013     1     1
##  9  2013     1     1
## 10  2013     1     1
## # ... with 336,766 more rows



rowwise

概要

<概要>
・行単位でグループ化する
 - グループ単位の処理をする場合に必要な操作
・ungroup()でグループ化を解除することができる



使用例

# 行単位でグループ化
X <- iris6 %>% rowwise() %T>% print()
## Source: local data frame [6 x 5]
## Groups: <by row>
## 
## # A tibble: 6 x 5
##   Sepal.Length Sepal.Width Petal.Length Petal.Width    Species
## *        <dbl>       <dbl>        <dbl>       <dbl>     <fctr>
## 1          5.1         3.5          1.4         0.2     setosa
## 2          4.9         3.0          1.4         0.2     setosa
## 3          7.0         3.2          4.7         1.4 versicolor
## 4          6.4         3.2          4.5         1.5 versicolor
## 5          6.3         3.3          6.0         2.5  virginica
## 6          5.8         2.7          5.1         1.9  virginica
# グループ数を確認
X %>% n_groups()
## [1] 6



グループ情報

全体像

<概要>
・グループ化に付随する各種情報を取得する


<関数一覧>
・is.grouped_df :
・groups    :
・n_groups    :
・group_size   :
・group_vars   :並び順を降順に変換する(要素に-1を乗じる)
・grouped_df   :
・group_indices :
・top_n     :



is.grouped_df

概要

<概要>
・データフレームにグループ化が適用されているかを判定
 



使用例

# 準備:グループ化したデータフレームを作成
X <- iris6 %>% group_by(Species) %T>% print()
## # A tibble: 6 x 5
## # Groups:   Species [3]
##   Sepal.Length Sepal.Width Petal.Length Petal.Width    Species
##          <dbl>       <dbl>        <dbl>       <dbl>     <fctr>
## 1          5.1         3.5          1.4         0.2     setosa
## 2          4.9         3.0          1.4         0.2     setosa
## 3          7.0         3.2          4.7         1.4 versicolor
## 4          6.4         3.2          4.5         1.5 versicolor
## 5          6.3         3.3          6.0         2.5  virginica
## 6          5.8         2.7          5.1         1.9  virginica
# データフレームにグループ化が適用されているかを判定
X %>% is.grouped_df()
## [1] TRUE
# 元のデータフレームはグループ化が適用されていない
iris6 %>% is.grouped_df()
## [1] FALSE



groups

概要

<概要>
・適用されているグループ化のキーを取得
 



使用例

# 準備
X <- flights %>% 
       select(year, month, day) %>% 
       group_by(year, month, day) %T>% 
       print()
## # A tibble: 336,776 x 3
## # Groups:   year, month, day [365]
##     year month   day
##    <int> <int> <int>
##  1  2013     1     1
##  2  2013     1     1
##  3  2013     1     1
##  4  2013     1     1
##  5  2013     1     1
##  6  2013     1     1
##  7  2013     1     1
##  8  2013     1     1
##  9  2013     1     1
## 10  2013     1     1
## # ... with 336,766 more rows
# 適用されているグループ化のキーを取得
X %>% groups()
## [[1]]
## year
## 
## [[2]]
## month
## 
## [[3]]
## day



n_groups

概要

<概要>
・グループ化を適用したデータフレームのグループ数を取得
 - アトミックベクトルとして出力



使用例

# 準備:行単位でグループ化
X <- iris6 %>% rowwise() %T>% print()
## Source: local data frame [6 x 5]
## Groups: <by row>
## 
## # A tibble: 6 x 5
##   Sepal.Length Sepal.Width Petal.Length Petal.Width    Species
## *        <dbl>       <dbl>        <dbl>       <dbl>     <fctr>
## 1          5.1         3.5          1.4         0.2     setosa
## 2          4.9         3.0          1.4         0.2     setosa
## 3          7.0         3.2          4.7         1.4 versicolor
## 4          6.4         3.2          4.5         1.5 versicolor
## 5          6.3         3.3          6.0         2.5  virginica
## 6          5.8         2.7          5.1         1.9  virginica
# グループ数を確認
X %>% n_groups()
## [1] 6



group_size

概要

<概要>
・グループごとのレコード数を取得
 - ベクトル形式で取得
 



使用例

# 準備:グループ化したデータフレームを作成
X <- iris6 %>% group_by(Species) %T>% print()
## # A tibble: 6 x 5
## # Groups:   Species [3]
##   Sepal.Length Sepal.Width Petal.Length Petal.Width    Species
##          <dbl>       <dbl>        <dbl>       <dbl>     <fctr>
## 1          5.1         3.5          1.4         0.2     setosa
## 2          4.9         3.0          1.4         0.2     setosa
## 3          7.0         3.2          4.7         1.4 versicolor
## 4          6.4         3.2          4.5         1.5 versicolor
## 5          6.3         3.3          6.0         2.5  virginica
## 6          5.8         2.7          5.1         1.9  virginica
# グループごとのレコード数を取得
X %>% group_size()
## [1] 2 2 2



group_vars

概要

使用例

grouped_df

概要

使用例

group_indices

概要

<概要>
・行ごとに含まれるグループのインデックスを取得
 



使用例

# グループごとのインデックスを出力
iris6 %>% group_indices(Species) 
## [1] 1 1 2 2 3 3



top_n

概要

<概要>
・



使用例

library(Lahman)
tbl_df(Batting) %>%
  group_by(playerID) %>%
  tally(G) %>%
  top_n(10)
## Selecting by n
## # A tibble: 10 x 2
##     playerID     n
##        <chr> <int>
##  1 aaronha01  3298
##  2 bondsba01  2986
##  3  cobbty01  3035
##  4 henderi01  3081
##  5  mayswi01  2992
##  6 murraed02  3026
##  7 musiast01  3026
##  8 ripkeca01  3001
##  9  rosepe01  3562
## 10 yastrca01  3308



## グループ集計 ### 全体像

<概要>
・グループ化したデータフレームをグループ単位に集計する
  - グループごとに1レコードに集約される
  


<関数一覧>
・summarise    :全ての列に複数の関数を一括適用して集計
・summarise_all :全ての列に複数の関数を一括適用して集計
・summarise_at :条件に一致したカラムに対して関数を適用
・summarise_if :カラムの内容が条件にマッチしたカラムに関数を適用する


<リタイア予定>
- summarise_each  特定条件の列に複数の関数を一括適用して集計


<別名関数>
- summarise関数群の別名として、summarize関数群が存在する



summarise

概要

<概要>
・グループ単位に集計を行う
  - group_by関数によるグループ化の適用が前提となる
  - 

・集計した結果は新しいデータセットとして扱われる
 - 集計列とグループ化キー列のみのデータセットとなる
  - グループ化は適用されていない



使用例

# 準備:グループ化したデータフレームを作成
X <- iris6 %>% group_by(Species) %T>% print()
## # A tibble: 6 x 5
## # Groups:   Species [3]
##   Sepal.Length Sepal.Width Petal.Length Petal.Width    Species
##          <dbl>       <dbl>        <dbl>       <dbl>     <fctr>
## 1          5.1         3.5          1.4         0.2     setosa
## 2          4.9         3.0          1.4         0.2     setosa
## 3          7.0         3.2          4.7         1.4 versicolor
## 4          6.4         3.2          4.5         1.5 versicolor
## 5          6.3         3.3          6.0         2.5  virginica
## 6          5.8         2.7          5.1         1.9  virginica
# グループごとに集計
# --- グループ化のキー列と集計値のデータセット
Y <- X %>% summarise(Mean = mean(Sepal.Length)) %T>% print()
## # A tibble: 3 x 2
##      Species  Mean
##       <fctr> <dbl>
## 1     setosa  5.00
## 2 versicolor  6.70
## 3  virginica  6.05
# 集計結果は新しいデータセットなのでグループ化はされていない
Y %>% is.grouped_df()
## [1] FALSE



応用1:グループ集計と全体集計

<ポイント>
・通常関数はグループ内で適用される
  - グループ化の適用に関わらずデータセット全体に適用できる関数もある
# グループ集計と全体集計
iris9 %>% 
  group_by(Species) %>% 
  summarise(Count_Group = n(), 
            Count_All   = nrow(.))
## # A tibble: 3 x 3
##      Species Count_Group Count_All
##       <fctr>       <int>     <int>
## 1     setosa           3         9
## 2 versicolor           3         9
## 3  virginica           3         9



課題:複数列の集計は面倒

<ポイント>
- 複数列の集計となると当然冗長な記述となる
iris6 %>% 
  group_by(Species) %>% 
  summarise(Sepal.Length_sum  = mean(Sepal.Length), 
            Sepal.Length_mean = mean(Sepal.Length), 
            Sepal.Width_sum   = mean(Sepal.Width), 
            Sepal.Width_mean  = mean(Sepal.Width)
            )
## # A tibble: 3 x 5
##      Species Sepal.Length_sum Sepal.Length_mean Sepal.Width_sum
##       <fctr>            <dbl>             <dbl>           <dbl>
## 1     setosa             5.00              5.00            3.25
## 2 versicolor             6.70              6.70            3.20
## 3  virginica             6.05              6.05            3.00
## # ... with 1 more variables: Sepal.Width_mean <dbl>



summrise_all

概要

<概要>
・すべての列に指定した関数を適用して集計することができる
iris %>% 
  group_by(Species) %>% 
  summarise_all(funs(min, mean, max))%>% {
    head(.) %>% print()
    str(.) %>% print()
  }
## # A tibble: 3 x 13
##      Species Sepal.Length_min Sepal.Width_min Petal.Length_min
##       <fctr>            <dbl>           <dbl>            <dbl>
## 1     setosa              4.3             2.3              1.0
## 2 versicolor              4.9             2.0              3.0
## 3  virginica              4.9             2.2              4.5
## # ... with 9 more variables: Petal.Width_min <dbl>,
## #   Sepal.Length_mean <dbl>, Sepal.Width_mean <dbl>,
## #   Petal.Length_mean <dbl>, Petal.Width_mean <dbl>,
## #   Sepal.Length_max <dbl>, Sepal.Width_max <dbl>, Petal.Length_max <dbl>,
## #   Petal.Width_max <dbl>
## Classes 'tbl_df', 'tbl' and 'data.frame':    3 obs. of  13 variables:
##  $ Species          : Factor w/ 3 levels "setosa","versicolor",..: 1 2 3
##  $ Sepal.Length_min : num  4.3 4.9 4.9
##  $ Sepal.Width_min  : num  2.3 2 2.2
##  $ Petal.Length_min : num  1 3 4.5
##  $ Petal.Width_min  : num  0.1 1 1.4
##  $ Sepal.Length_mean: num  5.01 5.94 6.59
##  $ Sepal.Width_mean : num  3.43 2.77 2.97
##  $ Petal.Length_mean: num  1.46 4.26 5.55
##  $ Petal.Width_mean : num  0.246 1.326 2.026
##  $ Sepal.Length_max : num  5.8 7 7.9
##  $ Sepal.Width_max  : num  4.4 3.4 3.8
##  $ Petal.Length_max : num  1.9 5.1 6.9
##  $ Petal.Width_max  : num  0.6 1.8 2.5
## NULL



summarise_at

<ポイント>
- 指定した列に対して指定した複数関数を適用して集計することができる
- 列の条件指定を応用すると柔軟さが増す
iris %>% 
  group_by(Species) %>% 
  summarise_at(vars(starts_with("Sepal")), funs(min, max)) %>% {
    head(.) %>% print()
    str(.) %>% print()
  }
## # A tibble: 3 x 5
##      Species Sepal.Length_min Sepal.Width_min Sepal.Length_max
##       <fctr>            <dbl>           <dbl>            <dbl>
## 1     setosa              4.3             2.3              5.8
## 2 versicolor              4.9             2.0              7.0
## 3  virginica              4.9             2.2              7.9
## # ... with 1 more variables: Sepal.Width_max <dbl>
## Classes 'tbl_df', 'tbl' and 'data.frame':    3 obs. of  5 variables:
##  $ Species         : Factor w/ 3 levels "setosa","versicolor",..: 1 2 3
##  $ Sepal.Length_min: num  4.3 4.9 4.9
##  $ Sepal.Width_min : num  2.3 2 2.2
##  $ Sepal.Length_max: num  5.8 7 7.9
##  $ Sepal.Width_max : num  4.4 3.4 3.8
## NULL



summarise_if

<ポイント>
- 条件に適合する列に対して指定した複数関数を適用して集計することができる
- 第1引数の関数にはカッコ()を付けない、is.numeric()ではない
iris %>% 
  group_by(Species) %>% 
  summarise_if(is.numeric, funs(min, max)) %>% {
    head(.) %>% print()
    str(.) %>% print()
  }
## # A tibble: 3 x 9
##      Species Sepal.Length_min Sepal.Width_min Petal.Length_min
##       <fctr>            <dbl>           <dbl>            <dbl>
## 1     setosa              4.3             2.3              1.0
## 2 versicolor              4.9             2.0              3.0
## 3  virginica              4.9             2.2              4.5
## # ... with 5 more variables: Petal.Width_min <dbl>,
## #   Sepal.Length_max <dbl>, Sepal.Width_max <dbl>, Petal.Length_max <dbl>,
## #   Petal.Width_max <dbl>
## Classes 'tbl_df', 'tbl' and 'data.frame':    3 obs. of  9 variables:
##  $ Species         : Factor w/ 3 levels "setosa","versicolor",..: 1 2 3
##  $ Sepal.Length_min: num  4.3 4.9 4.9
##  $ Sepal.Width_min : num  2.3 2 2.2
##  $ Petal.Length_min: num  1 3 4.5
##  $ Petal.Width_min : num  0.1 1 1.4
##  $ Sepal.Length_max: num  5.8 7 7.9
##  $ Sepal.Width_max : num  4.4 3.4 3.8
##  $ Petal.Length_max: num  1.9 5.1 6.9
##  $ Petal.Width_max : num  0.6 1.8 2.5
## NULL



summarise_each:非推奨

<ポイント>
- 条件一致するフィールドに特定関数を一律に適用する
- summarise_each関数は非推奨となった(後述)

<課題>
カラムの中身に条件をつけることはができなかった
- factor型のカラムをすべてcharacter型に変換する
- 数値だったらround()で小数点を丸める
# summarise_each関数(非推奨)
iris %>% 
  group_by(Species) %>% 
  summarise_each(funs(min, max), starts_with("Sepal")) %>% {
    head(.) %>% print()
    str(.) %>% print()
  }
## `summarise_each()` is deprecated.
## Use `summarise_all()`, `summarise_at()` or `summarise_if()` instead.
## To map `funs` over a selection of variables, use `summarise_at()`
## # A tibble: 3 x 5
##      Species Sepal.Length_min Sepal.Width_min Sepal.Length_max
##       <fctr>            <dbl>           <dbl>            <dbl>
## 1     setosa              4.3             2.3              5.8
## 2 versicolor              4.9             2.0              7.0
## 3  virginica              4.9             2.2              7.9
## # ... with 1 more variables: Sepal.Width_max <dbl>
## Classes 'tbl_df', 'tbl' and 'data.frame':    3 obs. of  5 variables:
##  $ Species         : Factor w/ 3 levels "setosa","versicolor",..: 1 2 3
##  $ Sepal.Length_min: num  4.3 4.9 4.9
##  $ Sepal.Width_min : num  2.3 2 2.2
##  $ Sepal.Length_max: num  5.8 7 7.9
##  $ Sepal.Width_max : num  4.4 3.4 3.8
## NULL



グループ処理

全体像

<概要>
・グループごとに集計以外の処理を行いたい場合は「do()」を用いる


<関数一覧>
・do  :グループ単位に関数を適用する


<代替処理>
・{purrr}



do

概要

<概要>
・データフレームのグループごとに集計以外の処理を行う
 - 事前にグループ化してあることが前提となる


<注意点>
・並列処理を行っていないので、数が増えると処理が遅くなる
 - {snowfall}のsflapply()などの使用も検討


<類似処理>
・purrr::map()など

使用例

# グループごとにtail()を適用
iris %>% group_by(Species) %>% do(tail(., 1))
## # A tibble: 3 x 5
## # Groups:   Species [3]
##   Sepal.Length Sepal.Width Petal.Length Petal.Width    Species
##          <dbl>       <dbl>        <dbl>       <dbl>     <fctr>
## 1          5.0         3.3          1.4         0.2     setosa
## 2          5.7         2.8          4.1         1.3 versicolor
## 3          5.9         3.0          5.1         1.8  virginica



条件分岐

全体像

<全体像>
・{dplyr}では条件分岐の関数を独自に定義している


<関数一覧>
・if_else  :base::ifelse()と同様だが、動作速度が速い
・case_when :base::switch()と同様だが、動作速度が速い
・na_if   :指定した数値や文字をNAに置換する
・coalesce   :各行で欠損じゃない最初の値を見つけてきて持ってくる



if_else

概要

<ポイント>
- base::ifelse()と同様だが、動作速度が速い
 - 欠損値の場合の対応を明示的に記述できる


<構文>
if_else(condition, true, false, missing = NULL)



使用例

# ベクトルの場合
x <- c(-3:3, NA) 
if_else(x < 0, "negative", "positive", "missing")
## [1] "negative" "negative" "negative" "positive" "positive" "positive"
## [7] "positive" "missing"
# データフレームの場合
# --- mutate()での使用
iris6 %>% 
  select(Species) %>% 
  mutate('setosa' = if_else(Species == "setosa", "SETOSA", "NA"))
## # A tibble: 6 x 2
##      Species setosa
##       <fctr>  <chr>
## 1     setosa SETOSA
## 2     setosa SETOSA
## 3 versicolor     NA
## 4 versicolor     NA
## 5  virginica     NA
## 6  virginica     NA
# データフレームの場合
# --- summarise()での使用
iris %>% 
  select(Species, Sepal.Length) %>% 
  group_by(Species) %>% 
  summarise('setosa' = mean(if_else(Species == "setosa", Sepal.Length, 0)))
## # A tibble: 3 x 2
##      Species setosa
##       <fctr>  <dbl>
## 1     setosa  5.006
## 2 versicolor  0.000
## 3  virginica  0.000



case_when

概要

使用例

na_if

概要

<概要>
・指定した数値や文字をNAに置換する
  - x[x == y] = NA; x のショートカット


<構文>
na_if(x, y)

x :修正したいベクトル
y :NAに置換する数値や文字



使用例

# ベクトルの場合
-5:5 %>% na_if(0)
##  [1] -5 -4 -3 -2 -1 NA  1  2  3  4  5
# データフレームの場合
iris6 %>% 
  select(Species, Sepal.Length) %>% 
  mutate(Species2      = na_if(Species, "versicolor"))
## # A tibble: 6 x 3
##      Species Sepal.Length  Species2
##       <fctr>        <dbl>    <fctr>
## 1     setosa          5.1    setosa
## 2     setosa          4.9    setosa
## 3 versicolor          7.0        NA
## 4 versicolor          6.4        NA
## 5  virginica          6.3 virginica
## 6  virginica          5.8 virginica



coalesce

概要

<概要>

- `coalesce()`は要素が`NA`の場合に次の条件の要素を補完していく
- `ifelse(!is.na(x), x, y)`のイメージ



例1:NA補完としての使い方

c(1, NA, NA, NA) %>% coalesce(0)
## [1] 1 0 0 0



例2:AVAIL的な使い方

x <- c(1, NA, NA, NA)
y <- c(2,  2, NA, NA)
z <- c(3,  3, 3,  NA)
data_frame(x, y, z) %>% 
  mutate('coalesce' = coalesce(x, y, z))
## # A tibble: 4 x 4
##       x     y     z coalesce
##   <dbl> <dbl> <dbl>    <dbl>
## 1     1     2     3        1
## 2    NA     2     3        2
## 3    NA    NA     3        3
## 4    NA    NA    NA       NA



5 ウインドウ関数編

ランキング関数

全体像

<概要>
ランキング系の関数には、以下の6つの関数がある。

- `row_number`   昇順にランキングを付ける(同値の場合は最初に来た方を優先)
- `min_rank`      昇順にランキングを付ける(同値の場合は同順位、gapあり)
- `dense_rank`   昇順にランキングを付ける(同値の場合は同順位、gapなし)
- `percent_rank` min_rankを0~1にリスケール
- `cume_dist`     累積割合(percent_rankの累積和ではない)
- `ntile`       n個の群に分割する



row_number

概要

<概要>
・データセットの行番号又はランキングを返す
 - 同値に対して行番号に応じた別順位を付ける


<ポイント>
・引数なしの場合
  - データセットのレコード番号を返す

・引数に特定列を指定した場合
 - 当該列のデータのランキングを昇順で返す
 - desc()を使うと降順となる
  



例1:引数なし

# 引数なしの場合はレコード番号を返す
iris9 %>% mutate(NO = row_number())
## # A tibble: 9 x 6
##   Sepal.Length Sepal.Width Petal.Length Petal.Width    Species    NO
##          <dbl>       <dbl>        <dbl>       <dbl>     <fctr> <int>
## 1          5.1         3.5          1.4         0.2     setosa     1
## 2          4.9         3.0          1.4         0.2     setosa     2
## 3          4.7         3.2          1.3         0.2     setosa     3
## 4          7.0         3.2          4.7         1.4 versicolor     4
## 5          6.4         3.2          4.5         1.5 versicolor     5
## 6          6.9         3.1          4.9         1.5 versicolor     6
## 7          6.3         3.3          6.0         2.5  virginica     7
## 8          5.8         2.7          5.1         1.9  virginica     8
## 9          7.1         3.0          5.9         2.1  virginica     9



例2:引数に特定列を指定

# 昇順
iris6 %>% select(Sepal.Width) %>% mutate(NO_ASC = row_number(Sepal.Width))
## # A tibble: 6 x 2
##   Sepal.Width NO_ASC
##         <dbl>  <int>
## 1         3.5      6
## 2         3.0      2
## 3         3.2      3
## 4         3.2      4
## 5         3.3      5
## 6         2.7      1
# 降順
iris6 %>% select(Sepal.Width) %>% mutate(NO_ASC = row_number(desc(Sepal.Width)))
## # A tibble: 6 x 2
##   Sepal.Width NO_ASC
##         <dbl>  <int>
## 1         3.5      1
## 2         3.0      5
## 3         3.2      3
## 4         3.2      4
## 5         3.3      2
## 6         2.7      6



min_rank

概要

<概要>
・データセットの行番号又はランキングを返す
 - 同値に対して行番号に応じた別順位を付ける

<ポイント>
- 昇順にランキングを付ける(同値の場合は同順位、gapあり)
- gapありとは、同順位のランクを空けて数字で付ける
- NAのランキングはNAとなる
- 降順にしたい場合はdesc()を付ける



使用例

# 昇順
iris6 %>% 
  select(Sepal.Width) %>% 
  arrange(Sepal.Width) %>% 
  mutate(NO_ASC = min_rank(Sepal.Width))
## # A tibble: 6 x 2
##   Sepal.Width NO_ASC
##         <dbl>  <int>
## 1         2.7      1
## 2         3.0      2
## 3         3.2      3
## 4         3.2      3
## 5         3.3      5
## 6         3.5      6
# 降順
iris6 %>% 
  select(Sepal.Width) %>% 
  arrange(Sepal.Width) %>% 
  mutate(NO_ASC = min_rank(desc(Sepal.Width)))
## # A tibble: 6 x 2
##   Sepal.Width NO_ASC
##         <dbl>  <int>
## 1         2.7      6
## 2         3.0      5
## 3         3.2      3
## 4         3.2      3
## 5         3.3      2
## 6         3.5      1



dense_rank

概要

<概要>


<ポイント>
- 昇順にランキングを付ける(同値の場合は同順位、gapなし)
- gapなしとは、同順位の次のランクを次の数字で付ける
- NAのランキングはNAとなる
- 降順にしたい場合はdesc()を付ける

使用例

data_frame(x = c(5 , 1 , 2 , 2 , 3 , NA)) %>%
  mutate(dense_rank_ASC = dense_rank(x)) %>% 
  mutate(dense_rank_DESC = dense_rank(desc(x)))
## # A tibble: 6 x 3
##       x dense_rank_ASC dense_rank_DESC
##   <dbl>          <int>           <int>
## 1     5              4               1
## 2     1              1               4
## 3     2              2               3
## 4     2              2               3
## 5     3              3               2
## 6    NA             NA              NA



percent_rank

概要

<概要>


<ポイント>
- 昇順にパーセントランクを付ける(min_rankを0~1にリスケール)
- 順位ではないのでgapの概念は存在しない
- NAのランキングはNAとなる
- 降順にしたい場合はdesc()を付ける

使用例

# 昇順
iris9 %>% 
  select(Sepal.Width) %>% 
  arrange(Sepal.Width) %>% 
  mutate(Rank = percent_rank(Sepal.Width))
## # A tibble: 9 x 2
##   Sepal.Width  Rank
##         <dbl> <dbl>
## 1         2.7 0.000
## 2         3.0 0.125
## 3         3.0 0.125
## 4         3.1 0.375
## 5         3.2 0.500
## 6         3.2 0.500
## 7         3.2 0.500
## 8         3.3 0.875
## 9         3.5 1.000
# 降順
iris9 %>% 
  select(Sepal.Width) %>% 
  arrange(Sepal.Width) %>% 
  mutate(Rank = percent_rank(desc(Sepal.Width)))
## # A tibble: 9 x 2
##   Sepal.Width  Rank
##         <dbl> <dbl>
## 1         2.7 1.000
## 2         3.0 0.750
## 3         3.0 0.750
## 4         3.1 0.625
## 5         3.2 0.250
## 6         3.2 0.250
## 7         3.2 0.250
## 8         3.3 0.125
## 9         3.5 0.000



cume_dist

概要

<ポイント>
- 累積割合(percent_rankの累積和ではない)
- NAのランキングはNAとなる
- 降順にしたい場合はdesc()を付ける

使用例

data_frame(x = c(5 , 1 , 2 , 2 , 3 , NA)) %>%
  mutate(cume_dist_ASC = cume_dist(x)) %>% 
  mutate(cume_dist_DESC = cume_dist(desc(x)))
## # A tibble: 6 x 3
##       x cume_dist_ASC cume_dist_DESC
##   <dbl>         <dbl>          <dbl>
## 1     5           1.0            0.2
## 2     1           0.2            1.0
## 3     2           0.6            0.8
## 4     2           0.6            0.8
## 5     3           0.8            0.4
## 6    NA            NA             NA



ntile

概要

<ポイント>
- n個の群に分割する
- NAのランキングはNAとなる
- 降順にしたい場合はdesc()を付ける

使用例

# 昇順
iris9 %>% 
  select(Sepal.Width) %>% 
  arrange(Sepal.Width) %>% 
  mutate(Tile = ntile(Sepal.Width, 3))
## # A tibble: 9 x 2
##   Sepal.Width  Tile
##         <dbl> <int>
## 1         2.7     1
## 2         3.0     1
## 3         3.0     1
## 4         3.1     2
## 5         3.2     2
## 6         3.2     2
## 7         3.2     3
## 8         3.3     3
## 9         3.5     3
# 降順
iris9 %>% 
  select(Sepal.Width) %>% 
  arrange(Sepal.Width) %>% 
  mutate(Tile = ntile(desc(Sepal.Width), 3))
## # A tibble: 9 x 2
##   Sepal.Width  Tile
##         <dbl> <int>
## 1         2.7     3
## 2         3.0     3
## 3         3.0     3
## 4         3.1     2
## 5         3.2     1
## 6         3.2     2
## 7         3.2     2
## 8         3.3     1
## 9         3.5     1



オフセット関数

全体像

<概要>
・指定した列を前後にずらす
 - 前後のレコードの取得が容易になり、前日比などの時系列処理が容易になる
 - leadやlagに合わせてレコード数が増加することはない


<関数一覧>
・lead :レコードを上(前)にずらす
・lag :レコードを下(後)にずらす
・nth



lead

概要

<概要>
・レコードを上(前)にずらす
 - leadをとる


<構文>
lead(x, n = 1L, default = NA, order_by = NULL, ...)

使用例

# 単純なデータフレーム 
data_frame(x = c(1, 2, 3, 4, 5)) %>%
  mutate(lead_1 = lead(x),
         lead_2 = lead(x, 2), 
         lag_1  = lag(x), 
         lag_2  = lag(x, 2))
## # A tibble: 5 x 5
##       x lead_1 lead_2 lag_1 lag_2
##   <dbl>  <dbl>  <dbl> <dbl> <dbl>
## 1     1      2      3    NA    NA
## 2     2      3      4     1    NA
## 3     3      4      5     2     1
## 4     4      5     NA     3     2
## 5     5     NA     NA     4     3
# グループ化データフレーム
iris9 %>% 
  select(Species, Sepal.Length) %>% 
  group_by(Species) %>% 
  mutate(Sepal.Length_lead = lead(Sepal.Length))
## # A tibble: 9 x 3
## # Groups:   Species [3]
##      Species Sepal.Length Sepal.Length_lead
##       <fctr>        <dbl>             <dbl>
## 1     setosa          5.1               4.9
## 2     setosa          4.9               4.7
## 3     setosa          4.7                NA
## 4 versicolor          7.0               6.4
## 5 versicolor          6.4               6.9
## 6 versicolor          6.9                NA
## 7  virginica          6.3               5.8
## 8  virginica          5.8               7.1
## 9  virginica          7.1                NA



lag

概要

<概要>
・レコードを下(後)にずらす
 - lagをとる


<構文>
lag(x, n = 1L, default = NA, order_by = NULL, ...)

使用例

# 単純なデータフレーム 
data_frame(x = c(1, 2, 3, 4, 5)) %>%
  mutate(lead_1 = lead(x),
         lead_2 = lead(x, 2), 
         lag_1  = lag(x), 
         lag_2  = lag(x, 2))
## # A tibble: 5 x 5
##       x lead_1 lead_2 lag_1 lag_2
##   <dbl>  <dbl>  <dbl> <dbl> <dbl>
## 1     1      2      3    NA    NA
## 2     2      3      4     1    NA
## 3     3      4      5     2     1
## 4     4      5     NA     3     2
## 5     5     NA     NA     4     3
# グループ化データフレーム
iris9 %>% 
  select(Species, Sepal.Length) %>% 
  group_by(Species) %>% 
  mutate(Sepal.Length_lag = lag(Sepal.Length))
## # A tibble: 9 x 3
## # Groups:   Species [3]
##      Species Sepal.Length Sepal.Length_lag
##       <fctr>        <dbl>            <dbl>
## 1     setosa          5.1               NA
## 2     setosa          4.9              5.1
## 3     setosa          4.7              4.9
## 4 versicolor          7.0               NA
## 5 versicolor          6.4              7.0
## 6 versicolor          6.9              6.4
## 7  virginica          6.3               NA
## 8  virginica          5.8              6.3
## 9  virginica          7.1              5.8



nth

累積関数

概要

<概要>

累積関数も各種そろっている。


【演算】
- cumsum    累和
- cumprod   累積
- cummin    累積最小値
- cummax    累積最大値


【理論演算】
- cummean   累積平均
- cumall    部分all
- cumany    部分any



cummean

cumall

cumany

数値演算(全体)

<ポイント>
- データフレーム全体での数値演算を行う
data_frame(x = c(1, 2, 3, 4, 5)) %>%
  mutate(Cum_Sum = cumsum(x)) %>% 
  mutate(Cum_Prod = cumprod(x)) %>% 
  mutate(Cum_Mean = cummean(x)) %>% 
  mutate(Cum_Min = cummin(x)) %>% 
  mutate(Cum_Max = cummax(x))
## # A tibble: 5 x 6
##       x Cum_Sum Cum_Prod Cum_Mean Cum_Min Cum_Max
##   <dbl>   <dbl>    <dbl>    <dbl>   <dbl>   <dbl>
## 1     1       1        1      1.0       1       1
## 2     2       3        2      1.5       1       2
## 3     3       6        6      2.0       1       3
## 4     4      10       24      2.5       1       4
## 5     5      15      120      3.0       1       5



数値演算(グループ別)

<ポイント>
- グループ別での数値演算を行う
data_frame(x = rep(c(1, 2, 3, 4, 5), 2), 
           y = c(rep("A", 5), rep("B", 5))) %>%
  group_by(y) %>% 
  mutate(Cum_Sum = cumsum(x)) %>% 
  mutate(Cum_Prod = cumprod(x)) %>% 
  mutate(Cum_Mean = cummean(x)) %>% 
  mutate(Cum_Min = cummin(x)) %>% 
  mutate(Cum_Max = cummax(x))
## # A tibble: 10 x 7
## # Groups:   y [2]
##        x     y Cum_Sum Cum_Prod Cum_Mean Cum_Min Cum_Max
##    <dbl> <chr>   <dbl>    <dbl>    <dbl>   <dbl>   <dbl>
##  1     1     A       1        1      1.0       1       1
##  2     2     A       3        2      1.5       1       2
##  3     3     A       6        6      2.0       1       3
##  4     4     A      10       24      2.5       1       4
##  5     5     A      15      120      3.0       1       5
##  6     1     B       1        1      1.0       1       1
##  7     2     B       3        2      1.5       1       2
##  8     3     B       6        6      2.0       1       3
##  9     4     B      10       24      2.5       1       4
## 10     5     B      15      120      3.0       1       5



理論演算

<ポイント>
- cumall()やcumany()で理論演算子の累積判定を行うことができる
- グループ別も数値演算と同様に行う
data_frame(x = c(TRUE , TRUE ,  FALSE ,TRUE , TRUE)) %>%
  mutate(cumall = cumall(x)) %>%
  mutate(cumany = cumany(x))
## # A tibble: 5 x 3
##       x cumall cumany
##   <lgl>  <lgl>  <lgl>
## 1  TRUE   TRUE   TRUE
## 2  TRUE   TRUE   TRUE
## 3 FALSE  FALSE   TRUE
## 4  TRUE  FALSE   TRUE
## 5  TRUE  FALSE   TRUE


ローリング関数

概要

<概要>

ローリングはRcppRollパッケージを使って行う

- `roll_mean`   移動平均
- `roll_sum`    移動合計
- `roll_prod`    移動累積
- `roll_max`     移動最大値
- `roll_min`    移動最小値
- `roll_median`  移動中央値
- `roll_sd`      移動標準偏差
- `roll_var`     移動分散


<主なオプション項目>

- `n`           ウィンドウサイズ
- `weights`   各要素の重みを指定(ウィンドサイズと同じ長さのベクトル)
- `fill`        欠損値を何で埋めるかを指定
- `align`       ウインドウの位置を指定("left" or "center" or "right"を指定)
- `normalize`   重みをNormalizeするかどうかを指定
- `na.rm`       NAを削除するかどうかを指定



基本演算

<ポイント>
- n引数(ウインドウサイズ)とfill引数は必須
- デフォルトではalignはCenter(中心化)で計算される
- roll_sdとroll_varは4ウインドウ以上が必要
data_frame(x = 1:10) %>% 
  mutate(Roll_Mean   = roll_mean(  x, 3, fill = NA)) %>% 
  mutate(Roll_Sum    = roll_sum(   x, 3, fill = NA)) %>% 
  mutate(Roll_Prod   = roll_prod(  x, 3, fill = NA)) %>% 
  mutate(Roll_Max    = roll_max(   x, 3, fill = NA)) %>% 
  mutate(Roll_Min    = roll_min(   x, 3, fill = NA)) %>% 
  mutate(Roll_Median = roll_median(x, 3, fill = NA)) %>% 
  mutate(Roll_Sd     = roll_sd(    x, 4, fill = NA)) %>% 
  mutate(Roll_Var    = roll_var(   x, 4, fill = NA))
## # A tibble: 10 x 9
##        x Roll_Mean Roll_Sum Roll_Prod Roll_Max Roll_Min Roll_Median
##    <int>     <dbl>    <dbl>     <dbl>    <dbl>    <dbl>       <dbl>
##  1     1        NA       NA        NA       NA       NA          NA
##  2     2         2        6         6        3        1           2
##  3     3         3        9        24        4        2           3
##  4     4         4       12        60        5        3           4
##  5     5         5       15       120        6        4           5
##  6     6         6       18       210        7        5           6
##  7     7         7       21       336        8        6           7
##  8     8         8       24       504        9        7           8
##  9     9         9       27       720       10        8           9
## 10    10        NA       NA        NA       NA       NA          NA
## # ... with 2 more variables: Roll_Sd <dbl>, Roll_Var <dbl>



サンプルの取り方の指定

<ポイント>
- align引数は計算でウインドウサンプルをどのようにとるかを指定する
- "center" or "left" or "right"のいずれかを指定する
- sum関数の派生関数として、alignの初期値を定めた「suml関数」や「sumr関数」がある
data_frame(x = 1:10) %>% 
  mutate(Sum_Center  = roll_mean( x, 3, fill = NA, align = "center")) %>% 
  mutate(Sum_Left    = roll_mean( x, 3, fill = NA, align = "left")) %>% 
  mutate(Sum_Left_2  = roll_meanl(x, 3, fill = NA)) %>% 
  mutate(Sum_Right   = roll_mean( x, 3, fill = NA, align = "right")) %>% 
  mutate(Sum_Right_2 = roll_meanr(x, 3, fill = NA))
## # A tibble: 10 x 6
##        x Sum_Center Sum_Left Sum_Left_2 Sum_Right Sum_Right_2
##    <int>      <dbl>    <dbl>      <dbl>     <dbl>       <dbl>
##  1     1         NA        2          2        NA          NA
##  2     2          2        3          3        NA          NA
##  3     3          3        4          4         2           2
##  4     4          4        5          5         3           3
##  5     5          5        6          6         4           4
##  6     6          6        7          7         5           5
##  7     7          7        8          8         6           6
##  8     8          8        9          9         7           7
##  9     9          9       NA         NA         8           8
## 10    10         NA       NA         NA         9           9



加重ウエイトの指定

<ポイント>
- weight引数を指定することで加重ウエイトを演算に適用することができる
- ウインドウサイズと同じ要素数のベクトルで定義する
data_frame(x = 1:10) %>% 
  mutate(Mean112 = roll_sum( x, 3, fill = NA, weights = c(1, 1, 2))) %>% 
  mutate(Mean121 = roll_sum( x, 3, fill = NA, weights = c(1, 2, 1))) %>% 
  mutate(Mean211 = roll_sum( x, 3, fill = NA, weights = c(2, 1, 1)))
## # A tibble: 10 x 4
##        x Mean112 Mean121 Mean211
##    <int>   <dbl>   <dbl>   <dbl>
##  1     1      NA      NA      NA
##  2     2    6.75       6    5.25
##  3     3    9.75       9    8.25
##  4     4   12.75      12   11.25
##  5     5   15.75      15   14.25
##  6     6   18.75      18   17.25
##  7     7   21.75      21   20.25
##  8     8   24.75      24   23.25
##  9     9   27.75      27   26.25
## 10    10      NA      NA      NA



加重ウエイトの標準化

<ポイント>
- 加重ウエイトはnormalize引数がTRUEなので、ベクトル要素の合計が1になる必要はない
- normalize引数をFALSEにすると、weights引数のベクトルがそのまま適用される
data_frame(x = 1:10) %>% 
  mutate(Normalized = roll_sum( x, 3, fill = NA, weights = c(10, 10, 20), normalize = TRUE)) %>% 
  mutate(unNormalized = roll_sum( x, 3, fill = NA, weights = c(10, 10, 20), normalize = FALSE))
## # A tibble: 10 x 3
##        x Normalized unNormalized
##    <int>      <dbl>        <dbl>
##  1     1         NA           NA
##  2     2       6.75           90
##  3     3       9.75          130
##  4     4      12.75          170
##  5     5      15.75          210
##  6     6      18.75          250
##  7     7      21.75          290
##  8     8      24.75          330
##  9     9      27.75          370
## 10    10         NA           NA



フィルタキーとしての活用

概要

<概要>

- これまで`mutate()`中心に使っていたが、`filter()`でも活用余地が大きい
- `filter()`は、`mutate(ウインドウ関数)+filter`を一括で行うイメージ
- フィルタが目的なら直接`filter()`したほうがスッキリする



ランキングとフィルタ

<ポイント>
- ウインドウ関数で付与したランキングでフィルタする
data_frame(x = c(1 , 2, 3, 4, 5) , 
           y = c("aa" ,"aa" , "aa" , "bb" , "bb")) %>%
  group_by(y) %>%
  filter(min_rank(x) == 1)
## # A tibble: 2 x 2
## # Groups:   y [2]
##       x     y
##   <dbl> <chr>
## 1     1    aa
## 2     4    bb



累積とフィルタ

<ポイント>
- ウインドウ関数で計算した累積でフィルタする
data_frame(x = c(1, 2, 3, 4, 5)) %>%
   filter(cumsum(x) > 5)
## # A tibble: 3 x 1
##       x
##   <dbl>
## 1     3
## 2     4
## 3     5




6 データ結合編

全体像

追加結合

全体像

<概要>

- `a`と`b`についてキーが一致するものを結合する
- `結合`とは`a`と`b`の両方のフィールドが参照できるデータを作成することを言う

サンプルデータ

a <- data_frame(
  x1 = c("A", "B", "C") ,
  x2 = c(1, 2, 3)
)

b <- data_frame(
  x1 = c("A", "B", "D") ,
  x3 = c(TRUE , FALSE , TRUE)
)



inner_join

# aとbの両方にあるキーを基準に結合する
inner_join(a , b ,by = "x1")
## # A tibble: 2 x 3
##      x1    x2    x3
##   <chr> <dbl> <lgl>
## 1     A     1  TRUE
## 2     B     2 FALSE



left_join

# aのキーを基準に結合する
left_join(a , b ,by = "x1")
## # A tibble: 3 x 3
##      x1    x2    x3
##   <chr> <dbl> <lgl>
## 1     A     1  TRUE
## 2     B     2 FALSE
## 3     C     3    NA



right_join

# bのキーを基準に結合する
right_join(a , b ,by = "x1")
## # A tibble: 3 x 3
##      x1    x2    x3
##   <chr> <dbl> <lgl>
## 1     A     1  TRUE
## 2     B     2 FALSE
## 3     D    NA  TRUE
# 左肩参照のaとbを反対にしても同じ
left_join(b , a ,by = "x1")
## # A tibble: 3 x 3
##      x1    x3    x2
##   <chr> <lgl> <dbl>
## 1     A  TRUE     1
## 2     B FALSE     2
## 3     D  TRUE    NA



full_join

# aとbのすべてにあるキーを用いて結合する
full_join(a , b ,by = "x1")
## # A tibble: 4 x 3
##      x1    x2    x3
##   <chr> <dbl> <lgl>
## 1     A     1  TRUE
## 2     B     2 FALSE
## 3     C     3    NA
## 4     D    NA  TRUE



複数キーで結合

a <- data_frame(
  x1 = c("A", "B", "C") ,
  x2 = c(1, 1, 1),
  x3 = c(1, 2, 3)
)

b <- data_frame(
  x1 = c("A", "B", "D") ,
  x2 = c(2, 1, 3),
  x4 = c(TRUE , FALSE , TRUE)
)

inner_join(a , b ,by = c("x1", "x2"))
## # A tibble: 1 x 4
##      x1    x2    x3    x4
##   <chr> <dbl> <dbl> <lgl>
## 1     B     1     2 FALSE



列名が異なるキーで結合

a <- data_frame(
  x1 = c("A", "B", "C") ,
  x2 = c(1, 2, 3)
)

b <- data_frame(
  x2 = c("A", "B", "D") ,
  x3 = c(TRUE , FALSE , TRUE)
)

inner_join(a , b ,by = c("x1" = "x2"))
## # A tibble: 2 x 3
##      x1    x2    x3
##   <chr> <dbl> <lgl>
## 1     A     1  TRUE
## 2     B     2 FALSE



列名が異なる複数列をキーで結合

a <- data_frame(
  a1 = c("A", "B", "C") ,
  a2 = c(1, 1, 1),
  a3 = c(1, 2, 3)
)

b <- data_frame(
  b1 = c("A", "B", "D") ,
  b2 = c(2, 1, 3),
  b3 = c(TRUE , FALSE , TRUE)
)

inner_join(a , b ,by = c("a1" ="b1" , "a2" = "b2"))
## # A tibble: 1 x 4
##      a1    a2    a3    b3
##   <chr> <dbl> <dbl> <lgl>
## 1     B     1     2 FALSE




フィルタ結合

全体像

<概要>

- `x`の行のフィルタリングに、`y`とマッチしたか否かを使用する
- `x`に`y`のデータ結合は行われない



サンプルデータ

a <- data_frame(
  x1 = c("A", "B", "C") ,
  x2 = c(1, 2, 3)
)

b <- data_frame(
  x1 = c("A", "B", "D") ,
  x3 = c(TRUE , FALSE , TRUE)
)



semi_join

# yにもあるxのレコードを返す
semi_join(a, b, by = "x1")
## # A tibble: 2 x 2
##      x1    x2
##   <chr> <dbl>
## 1     A     1
## 2     B     2



anti_join

# yにはないxのレコードを返す
anti_join(a, b, by = "x1")
## # A tibble: 1 x 2
##      x1    x2
##   <chr> <dbl>
## 1     C     3



連結結合

全体像

<概要>

- 同じ形式のデータフレームに対して`連結結合`などを行う

サンプルデータ

a <- dplyr::data_frame(
  x1 = c("A","B","C") ,
  x2 = c( 1 , 2 , 3 )
)

b <- dplyr::data_frame(
  x1 = c("B","C","D"),
  x2 = c( 2 , 3 , 4)
)



union

union(a, b)
## # A tibble: 4 x 2
##      x1    x2
##   <chr> <dbl>
## 1     B     2
## 2     C     3
## 3     A     1
## 4     D     4



union_all

union_all(a, b)
## # A tibble: 6 x 2
##      x1    x2
##   <chr> <dbl>
## 1     A     1
## 2     B     2
## 3     C     3
## 4     B     2
## 5     C     3
## 6     D     4



bind_rows

bind_cols

rbind_all

rbind_list

combine

intersect

intersect(a, b)
## # A tibble: 2 x 2
##      x1    x2
##   <chr> <dbl>
## 1     B     2
## 2     C     3



setdiff

setdiff(a, b)
## # A tibble: 1 x 2
##      x1    x2
##   <chr> <dbl>
## 1     A     1



setequal

# 単純なケース
setequal(a, b)
## FALSE: Rows in x but not y: 1. Rows in y but not x: 3.
setequal(a , a)
## TRUE
# xをランダムに入れ替えても当然TRUE
setequal(a , a[order(sample(1:3)), ])
## TRUE




7 データ集計

カウント

n

概要

<概要>
・データフレームのレコード数をグループごとにカウントする
  - グループ化した場合はグループごとに適用


<全体集計>
・グループ化しても列全体の最初の値を取得することも可能
  - nrow()を使っても全体集計が可能
  - n()は列を選択しないので、「.$Colname」として列全体を選択する方法は不可



使用例

# グループ単位の集計
iris6 %>% group_by(Species) %>% summarise(n_Group = n(), 
                                          n_All   = nrow(.))
## # A tibble: 3 x 3
##      Species n_Group n_All
##       <fctr>   <int> <int>
## 1     setosa       2     6
## 2 versicolor       2     6
## 3  virginica       2     6



tally

概要

<概要>
・ グループごとのレコード数を集計結果として出力
  - `グループ化の列`と`レコード数`のみが出力される
  - `summarise(n = n())`と同様だが簡単にかける



使用例

# グループごとのレコード数を取得
iris6 %>% group_by(Species) %>% tally()
## # A tibble: 3 x 2
##      Species     n
##       <fctr> <int>
## 1     setosa     2
## 2 versicolor     2
## 3  virginica     2
# summarise() + n() で同様の操作が可能
iris6 %>% group_by(Species) %>% summarise(n = n())
## # A tibble: 3 x 2
##      Species     n
##       <fctr> <int>
## 1     setosa     2
## 2 versicolor     2
## 3  virginica     2



count

概要

<概要>
・特定列のファクターごとのレコード数をカウントする
 - tally()のようにグループ化せず、直接列を指定することができる



使用例

# ファクターごとのレコード数をカウント
iris6 %>% count(Species)
## # A tibble: 3 x 2
##      Species     n
##       <fctr> <int>
## 1     setosa     2
## 2 versicolor     2
## 3  virginica     2
# 文字列でなく、数値でもカウント可能
iris6 %>% count(Sepal.Width)
## # A tibble: 5 x 2
##   Sepal.Width     n
##         <dbl> <int>
## 1         2.7     1
## 2         3.0     1
## 3         3.2     2
## 4         3.3     1
## 5         3.5     1



add_tally

概要

<概要>
・元のデータセットにグループ単位のカウント集計列を追加する
  - tally()は集計列のみを表示


<類似操作>
・tally()
・count()
・add_tally()
・add_count()



例1:全体集計

# 元のデータセットにカウント集計列を追加する
iris6 %>% add_tally()
## # A tibble: 6 x 6
##   Sepal.Length Sepal.Width Petal.Length Petal.Width    Species     n
##          <dbl>       <dbl>        <dbl>       <dbl>     <fctr> <int>
## 1          5.1         3.5          1.4         0.2     setosa     6
## 2          4.9         3.0          1.4         0.2     setosa     6
## 3          7.0         3.2          4.7         1.4 versicolor     6
## 4          6.4         3.2          4.5         1.5 versicolor     6
## 5          6.3         3.3          6.0         2.5  virginica     6
## 6          5.8         2.7          5.1         1.9  virginica     6
# 参考:カウントのみを表示
iris6 %>% tally()
## # A tibble: 1 x 1
##       n
##   <int>
## 1     6



例2:グループ集計

# 元のデータセットにカウント集計列を追加する
iris6 %>% group_by(Species) %>% add_tally()
## # A tibble: 6 x 6
## # Groups:   Species [3]
##   Sepal.Length Sepal.Width Petal.Length Petal.Width    Species     n
##          <dbl>       <dbl>        <dbl>       <dbl>     <fctr> <int>
## 1          5.1         3.5          1.4         0.2     setosa     2
## 2          4.9         3.0          1.4         0.2     setosa     2
## 3          7.0         3.2          4.7         1.4 versicolor     2
## 4          6.4         3.2          4.5         1.5 versicolor     2
## 5          6.3         3.3          6.0         2.5  virginica     2
## 6          5.8         2.7          5.1         1.9  virginica     2
# 参考:カウントのみを表示
iris6 %>% group_by(Species) %>% tally()
## # A tibble: 3 x 2
##      Species     n
##       <fctr> <int>
## 1     setosa     2
## 2 versicolor     2
## 3  virginica     2



add_count

概要

<概要>
・元のデータセットの特定列のカウント集計列を追加する
  - count()は集計列のみを表示


<類似操作>
・tally()
・count()
・add_tally()
・add_count()



使用例

iris6 %>% add_count(Sepal.Width)
## # A tibble: 6 x 6
##   Sepal.Length Sepal.Width Petal.Length Petal.Width    Species     n
##          <dbl>       <dbl>        <dbl>       <dbl>     <fctr> <int>
## 1          5.1         3.5          1.4         0.2     setosa     1
## 2          4.9         3.0          1.4         0.2     setosa     1
## 3          7.0         3.2          4.7         1.4 versicolor     2
## 4          6.4         3.2          4.5         1.5 versicolor     2
## 5          6.3         3.3          6.0         2.5  virginica     1
## 6          5.8         2.7          5.1         1.9  virginica     1



レコード指定

first

概要

<概要>
・データフレームの指定した列の最初の要素を取得
 - グループ化した場合はグループごとに適用


<全体集計>
・グループ化しても列全体の最初の値を取得することも可能
  - 「.$Colname」として列全体を選択する


<類似関数>
・last()
・nth()

使用例

# ベクトルでの使用
1:10 %>% first()
## [1] 1
# データフレームでの使用
# --- 
iris6 %>% 
  select(Species, Sepal.Length) %>% 
  group_by(Species) %>% 
  mutate(First_Group = first(Sepal.Length), 
         First_All   = first(.$Sepal.Length))
## # A tibble: 6 x 4
## # Groups:   Species [3]
##      Species Sepal.Length First_Group First_All
##       <fctr>        <dbl>       <dbl>     <dbl>
## 1     setosa          5.1         5.1       5.1
## 2     setosa          4.9         5.1       5.1
## 3 versicolor          7.0         7.0       5.1
## 4 versicolor          6.4         7.0       5.1
## 5  virginica          6.3         6.3       5.1
## 6  virginica          5.8         6.3       5.1



last

概要

<概要>
・データフレームの指定した列の最後の要素を取得
 - グループ化した場合はグループごとに適用


<全体集計>
・グループ化しても列全体の最後の値を取得することも可能
  - 「.$Colname」として列全体を選択する


<類似関数>
・first()
・nth()

使用例

# ベクトルでの使用
1:10 %>% last()
## [1] 10
# データフレームでの使用
# --- 
iris6 %>% 
  select(Species, Sepal.Length) %>% 
  group_by(Species) %>% 
  mutate(Last_Group = last(Sepal.Length), 
         Last_All   = last(.$Sepal.Length))
## # A tibble: 6 x 4
## # Groups:   Species [3]
##      Species Sepal.Length Last_Group Last_All
##       <fctr>        <dbl>      <dbl>    <dbl>
## 1     setosa          5.1        4.9      5.8
## 2     setosa          4.9        4.9      5.8
## 3 versicolor          7.0        6.4      5.8
## 4 versicolor          6.4        6.4      5.8
## 5  virginica          6.3        5.8      5.8
## 6  virginica          5.8        5.8      5.8



nth

概要


<概要>
・データフレームの指定した列の指定番号の要素を取得
 - グループ化した場合はグループごとに適用


<全体集計>
・グループ化しても列全体の最後の値を取得することも可能
  - 「.$Colname」として列全体を選択する


<類似関数>
・first()
・last()



使用例

# ベクトルでの使用
1:10 %>% nth(5)
## [1] 5
# データフレームでの使用
# --- 
iris9 %>% 
  select(Species, Sepal.Length) %>% 
  group_by(Species) %>% 
  mutate(Last_Group = nth(Sepal.Length, 2), 
         Last_All   = nth(.$Sepal.Length, 2))
## # A tibble: 9 x 4
## # Groups:   Species [3]
##      Species Sepal.Length Last_Group Last_All
##       <fctr>        <dbl>      <dbl>    <dbl>
## 1     setosa          5.1        4.9      4.9
## 2     setosa          4.9        4.9      4.9
## 3     setosa          4.7        4.9      4.9
## 4 versicolor          7.0        6.4      4.9
## 5 versicolor          6.4        6.4      4.9
## 6 versicolor          6.9        6.4      4.9
## 7  virginica          6.3        5.8      4.9
## 8  virginica          5.8        5.8      4.9
## 9  virginica          7.1        5.8      4.9



レコード操作

recode

概要

<概要>
・ベクトルの指定した要素を置換する
  - 「if_else()」や「case_when()」といった条件分岐を使用せずに要素置換を実現
  



使用例

# ベクトルの場合
LETTERS[1:5] %>% recode(A = 'a', E = 'e')
## [1] "a" "B" "C" "D" "e"
# データフレームの場合
iris6 %>% mutate(Species2 = recode(Species, 
                                   setosa     = 'set', 
                                   versicolor = 'ver', 
                                   virginica  = 'vir'))
## # A tibble: 6 x 6
##   Sepal.Length Sepal.Width Petal.Length Petal.Width    Species Species2
##          <dbl>       <dbl>        <dbl>       <dbl>     <fctr>   <fctr>
## 1          5.1         3.5          1.4         0.2     setosa      set
## 2          4.9         3.0          1.4         0.2     setosa      set
## 3          7.0         3.2          4.7         1.4 versicolor      ver
## 4          6.4         3.2          4.5         1.5 versicolor      ver
## 5          6.3         3.3          6.0         2.5  virginica      vir
## 6          5.8         2.7          5.1         1.9  virginica      vir



recode_factor

概要

<概要>
・ベクトルの指定した要素を置換する
  - 「if_else()」や「case_when()」といった条件分岐を使用せずに要素置換を実現
  



使用例

# ベクトルの場合
LETTERS[1:5] %>% recode_factor(A = 'a', E = 'e')

# データフレームの場合
iris6 %>% mutate(Species2 = recode(Species, 
                                   setosa     = 'set', 
                                   versicolor = 'ver', 
                                   virginica  = 'vir'))



between

概要

<概要>
・ベクトルの要素が指定範囲内かどうかでTRUE/FALSEを返す
  - 数値に対して適用できる
 - left <= x & x <= right のショートカット
 

<構文>
between(x, left, right)



例1:ベクトルでの適用

# ベクトルでの使用
1:10 %>% between(4, 6)
##  [1] FALSE FALSE FALSE  TRUE  TRUE  TRUE FALSE FALSE FALSE FALSE



例2:データフレームでの適用

# データフレームでの使用
iris6 %>% 
  select(Sepal.Length) %>% 
  arrange(Sepal.Length) %>% 
  mutate(SL_5 = if_else(between(Sepal.Length, 5, 6), 1, 0))
## # A tibble: 6 x 2
##   Sepal.Length  SL_5
##          <dbl> <dbl>
## 1          4.9     0
## 2          5.1     1
## 3          5.8     1
## 4          6.3     0
## 5          6.4     0
## 6          7.0     0



near

集計関数の基本

概要

  • グループ化したらsummarise()mutate()で集計データを作成する
    • summarise():グループごとに列を集約して演算
    • mutate()  :グループごとに列の集約はしないで演算
# データセットの準備
X <- iris %>% group_by(Species) %>% do(head(., 3))



summarise関数

<ポイント>
- summarise関数はグループ化で指定した主キーでレコードの絞り込みが行われる
- 「.」がユニバース全体を示している
- `grouped_dfクラス`ではグループ化された状態が基本なので、「.$」は省略可能
- summarise関数と対応関係にある
# m列はグループ集計、n列は全体集計
# --- mutate関数と違い、レコードの絞り込みが行われた状態で表示される
X %>% summarise(COUNT = n(), 
                COUNT_ALL = nrow(.),   
                MEAN_SL = mean(Sepal.Length))
## # A tibble: 3 x 4
##      Species COUNT COUNT_ALL  MEAN_SL
##       <fctr> <int>     <int>    <dbl>
## 1     setosa     3         9 4.900000
## 2 versicolor     3         9 6.766667
## 3  virginica     3         9 6.400000
# m列はグループを指定、m列はあくまで全体指定でval列でチェックしているだけ
X %>% summarise(MEAN_SL = mean(Sepal.Length), 
                MEAN_SL_ALL = mean(.$Sepal.Length))
## # A tibble: 3 x 3
##      Species  MEAN_SL MEAN_SL_ALL
##       <fctr>    <dbl>       <dbl>
## 1     setosa 4.900000    6.022222
## 2 versicolor 6.766667    6.022222
## 3  virginica 6.400000    6.022222



mutate関数

<ポイント>
- mutate関数はレコードの絞り込みは行わない
    - 集計関数によって各レコードに集計値を表示することが可能
- 「.(ドット)」がユニバース全体を示している
- `grouped_dfクラス`ではグループ化された状態が基本なので、「.$」は省略可能
- summarise関数と対応関係にある
# m列はグループ集計、n列は全体集計
X %>% mutate(Mean = mean(Sepal.Length), 
             Mean_All = mean(.$Sepal.Length))
## # A tibble: 9 x 7
## # Groups:   Species [3]
##   Sepal.Length Sepal.Width Petal.Length Petal.Width    Species     Mean
##          <dbl>       <dbl>        <dbl>       <dbl>     <fctr>    <dbl>
## 1          5.1         3.5          1.4         0.2     setosa 4.900000
## 2          4.9         3.0          1.4         0.2     setosa 4.900000
## 3          4.7         3.2          1.3         0.2     setosa 4.900000
## 4          7.0         3.2          4.7         1.4 versicolor 6.766667
## 5          6.4         3.2          4.5         1.5 versicolor 6.766667
## 6          6.9         3.1          4.9         1.5 versicolor 6.766667
## 7          6.3         3.3          6.0         2.5  virginica 6.400000
## 8          5.8         2.7          5.1         1.9  virginica 6.400000
## 9          7.1         3.0          5.9         2.1  virginica 6.400000
## # ... with 1 more variables: Mean_All <dbl>



グループ単位の関数適用

概要

<概要>
・グループ単位のデータセットに対して処理を行いたい場合は「do()」を使用する


<使用例>
・グループ単位にhead関数を適用
・グループ単位に回帰分析
・グループ単位に最適化問題
など



使用例

<ポイント>
・do()の第1引数は直前のデータを取る
・適用する関数内でもデータフレーム指定する必要がある
  - 直前のデータフレームは「.(ドット)」で指定する
# 通常の書き方
iris %>% group_by(Species) %>% do(head(., 2))
## # A tibble: 6 x 5
## # Groups:   Species [3]
##   Sepal.Length Sepal.Width Petal.Length Petal.Width    Species
##          <dbl>       <dbl>        <dbl>       <dbl>     <fctr>
## 1          5.1         3.5          1.4         0.2     setosa
## 2          4.9         3.0          1.4         0.2     setosa
## 3          7.0         3.2          4.7         1.4 versicolor
## 4          6.4         3.2          4.5         1.5 versicolor
## 5          6.3         3.3          6.0         2.5  virginica
## 6          5.8         2.7          5.1         1.9  virginica
# 参考:doの第1引数が直前データであること明示
iris %>% group_by(Species) %>% do(., head(., 2))
## # A tibble: 6 x 5
## # Groups:   Species [3]
##   Sepal.Length Sepal.Width Petal.Length Petal.Width    Species
##          <dbl>       <dbl>        <dbl>       <dbl>     <fctr>
## 1          5.1         3.5          1.4         0.2     setosa
## 2          4.9         3.0          1.4         0.2     setosa
## 3          7.0         3.2          4.7         1.4 versicolor
## 4          6.4         3.2          4.5         1.5 versicolor
## 5          6.3         3.3          6.0         2.5  virginica
## 6          5.8         2.7          5.1         1.9  virginica



do関数(応用)

<ポイント>
- do関数で複数の値をリストに入れても、summarise関数で1つにすれば表示できる
iris %>% 
  group_by(Species) %>% 
  do(sl_range = range(.$Sepal.Length) %>% format(2)) %>%
  summarise(sl_range = paste(sl_range[1], "-", sl_range[2]))
## # A tibble: 3 x 1
##    sl_range
##       <chr>
## 1 4.3 - 5.8
## 2 4.9 - 7.0
## 3 4.9 - 7.9



基本統計量の計算

概要

<概要>
- 基本的な関数を使ったレコード集計を確認する
- ここではレコード集計を`summarise関数`で行う



基本統計量

<ポイント>
- gruop_byを使うとgrouped_dfクラスが作成され、集計単位の基本はグループレベルとなる
- 普通に関数を適用すると集計が可能
# グループ集計と基本演算
iris %>% 
  select(Sepal.Length, Species) %>% 
  group_by(Species) %>% 
  summarise(SUM = sum(Sepal.Length), 
            MEAN = mean(Sepal.Length), 
            MEDIAN = median(Sepal.Length),
            MAX = max(Sepal.Length),
            MIN = min(Sepal.Length),
            RANGE = diff(range(Sepal.Length)),
            VAR = var(Sepal.Length),
            SD = sd(Sepal.Length)
            )
## # A tibble: 3 x 9
##      Species   SUM  MEAN MEDIAN   MAX   MIN RANGE       VAR        SD
##       <fctr> <dbl> <dbl>  <dbl> <dbl> <dbl> <dbl>     <dbl>     <dbl>
## 1     setosa 250.3 5.006    5.0   5.8   4.3   1.5 0.1242490 0.3524897
## 2 versicolor 296.8 5.936    5.9   7.0   4.9   2.1 0.2664327 0.5161711
## 3  virginica 329.4 6.588    6.5   7.9   4.9   3.0 0.4043429 0.6358796



レコード数のカウント1

<ポイント>
- n関数は{dplyr}で定義されているレコード数のカウント関数
- nrow関数はデータフレームのレコード数を返す関数
- 「.」はデータセット全体を示すのは同様
# グループ化あり
iris %>% 
  select(Sepal.Length, Species) %>% 
  group_by(Species) %>% 
  summarise(COUNT = n(), 
            COUNT_ALL = nrow(.)
            )
## # A tibble: 3 x 3
##      Species COUNT COUNT_ALL
##       <fctr> <int>     <int>
## 1     setosa    50       150
## 2 versicolor    50       150
## 3  virginica    50       150
# グループ化なし
iris %>% 
  select(Sepal.Length, Species) %>% 
  summarise(COUNT = n(), 
            COUNT_ALL = nrow(.)
            )
##   COUNT COUNT_ALL
## 1   150       150



レコード数のカウント2

<ポイント>
- summariseの中で集計関数を書かなくてもカウント集計が可能
- tally()とcount()は同様
- count()にはcount_()がある。NSE(Non-Standard Evaluation:非標準評価)
## 以下の3つはすべて同じ結果を返す

# summariseとn()を使う方法
iris %>% 
  select(Sepal.Length, Species) %>% 
  group_by(Species) %>% 
  summarise(COUNT = n())

# tally()
# summarise(x, n=n()) のショートカット。。
iris %>% 
  select(Sepal.Length, Species) %>% 
  group_by(Species) %>% 
  tally()

# count()
# group_by(...) %>% tally() のショートカット
iris %>% 
  select(Sepal.Length, Species) %>% 
  group_by(Species) %>% 
  count()



歪度と尖度

<ポイント>
- 歪度と尖度の関数はmomentsパッケージに登録されている
- ここではグループごとに集計する


参考資料:momentsパッケージ


# ライブラリの参照
library(moments)

# 計算
iris %>% 
  select(Sepal.Length, Species) %>% 
  group_by(Species) %>% 
  summarise(SKEW = skewness(Sepal.Length), 
            KURT = kurtosis(.$Sepal.Length) 
            )
## # A tibble: 3 x 3
##      Species      SKEW     KURT
##       <fctr>     <dbl>    <dbl>
## 1     setosa 0.1164539 2.426432
## 2 versicolor 0.1021896 2.426432
## 3  virginica 0.1144447 2.426432



条件付き集計

概要

<概要>

Excelの`sumif`や`countif`といった集計をdplyrで行う



[]演算子を使う方法

iris %>% 
  select(Sepal.Length, Species) %>% 
  group_by(Species) %>% 
  summarise('G1' = mean(Sepal.Length[Species == "setosa"]), 
            'G2' = mean(Sepal.Length[Species == "versicolor"]),
            'G3' = mean(Sepal.Length[Species == "virginica"]))
## # A tibble: 3 x 4
##      Species    G1    G2    G3
##       <fctr> <dbl> <dbl> <dbl>
## 1     setosa 5.006   NaN   NaN
## 2 versicolor   NaN 5.936   NaN
## 3  virginica   NaN   NaN 6.588



ifelseを使う方法

iris %>% 
  select(Sepal.Length, Species) %>% 
  group_by(Species) %>% 
  summarise('G1' = ifelse(Species == "setosa", Sepal.Length, 0) %>% mean(), 
            'G2' = ifelse(Species == "versicolor", Sepal.Length, 0) %>% mean(),
            'G3' = ifelse(Species == "virginica", Sepal.Length, 0) %>% mean())
## # A tibble: 3 x 4
##      Species    G1    G2    G3
##       <fctr> <dbl> <dbl> <dbl>
## 1     setosa 5.006 0.000 0.000
## 2 versicolor 0.000 5.936 0.000
## 3  virginica 0.000 0.000 6.588



if_elseを使う方法

iris %>% 
  select(Sepal.Length, Species) %>% 
  group_by(Species) %>% 
  summarise('G1' = if_else(Species == "setosa", Sepal.Length, 0) %>% mean(), 
            'G2' = if_else(Species == "versicolor", Sepal.Length, 0) %>% mean(),
            'G3' = if_else(Species == "virginica", Sepal.Length, 0) %>% mean())
## # A tibble: 3 x 4
##      Species    G1    G2    G3
##       <fctr> <dbl> <dbl> <dbl>
## 1     setosa 5.006 0.000 0.000
## 2 versicolor 0.000 5.936 0.000
## 3  virginica 0.000 0.000 6.588



{tidyr}を使う方法

library(tidyr)




全体像

<ポイント>

- 複数の入力レコードを集計して1つのレコードを出力する
    - group_by() + summarise()
    - 1つの値を返す = 1レコードに集約する


<Rの集約関数>
 min() 
 max() 
 mean() 
 sum() 
 sd() 
 median() 
 IQR() など


<dplyrの集約関数>  
 n()
 n_distinct()
 first
 last
 nth



8 行方向の集計

行単位のグループ化

概要

  • rowwise()を使うと行単位でグループ化することができる
    • 列方向の集計を想定した処理でmutate()で集計列を追加する
    • purrr::by_row()でも同様の操作が可能



rowwise関数

# 行単位でグループ化
X <- iris %>% rowwise() %T>% print()
## Source: local data frame [150 x 5]
## Groups: <by row>
## 
## # A tibble: 150 x 5
##    Sepal.Length Sepal.Width Petal.Length Petal.Width Species
##  *        <dbl>       <dbl>        <dbl>       <dbl>  <fctr>
##  1          5.1         3.5          1.4         0.2  setosa
##  2          4.9         3.0          1.4         0.2  setosa
##  3          4.7         3.2          1.3         0.2  setosa
##  4          4.6         3.1          1.5         0.2  setosa
##  5          5.0         3.6          1.4         0.2  setosa
##  6          5.4         3.9          1.7         0.4  setosa
##  7          4.6         3.4          1.4         0.3  setosa
##  8          5.0         3.4          1.5         0.2  setosa
##  9          4.4         2.9          1.4         0.2  setosa
## 10          4.9         3.1          1.5         0.1  setosa
## # ... with 140 more rows
# グループ数の確認
X %>% n_groups()
## [1] 150



集計列の追加:mutate()

# mutate関数で集計列を追加
X %>% mutate(mean = mean(Sepal.Length:Petal.Width))
## Source: local data frame [150 x 6]
## Groups: <by row>
## 
## # A tibble: 150 x 6
##    Sepal.Length Sepal.Width Petal.Length Petal.Width Species  mean
##           <dbl>       <dbl>        <dbl>       <dbl>  <fctr> <dbl>
##  1          5.1         3.5          1.4         0.2  setosa   3.1
##  2          4.9         3.0          1.4         0.2  setosa   2.9
##  3          4.7         3.2          1.3         0.2  setosa   2.7
##  4          4.6         3.1          1.5         0.2  setosa   2.6
##  5          5.0         3.6          1.4         0.2  setosa   3.0
##  6          5.4         3.9          1.7         0.4  setosa   2.9
##  7          4.6         3.4          1.4         0.3  setosa   2.6
##  8          5.0         3.4          1.5         0.2  setosa   3.0
##  9          4.4         2.9          1.4         0.2  setosa   2.4
## 10          4.9         3.1          1.5         0.1  setosa   2.9
## # ... with 140 more rows



集計列の追加:purrr::by_row()

# purrr::by_rowでも同様の操作が可能
iris %>% by_row(lift_vl(mean)) %>% unnest()



データフレームの転置

  • {dplyr}による処理は列単位で行われる
    • 行方向に処理したい場合は転置が必要となる
    • 参考資料
# 準備:データセットの作成
X <- 101:115 %>% matrix(5, 3) %>% as_tibble() %>% print()
## # A tibble: 5 x 3
##      V1    V2    V3
##   <int> <int> <int>
## 1   101   106   111
## 2   102   107   112
## 3   103   108   113
## 4   104   109   114
## 5   105   110   115
# t()による転置
X %>% t() %>% as_tibble()
## # A tibble: 3 x 5
##      V1    V2    V3    V4    V5
##   <int> <int> <int> <int> <int>
## 1   101   102   103   104   105
## 2   106   107   108   109   110
## 3   111   112   113   114   115
# {tidyr}による転置 
X %>% 
  rownames_to_column() %>% 
  gather(var, value, -rowname) %>% 
  spread(rowname, value)
## # A tibble: 3 x 6
##     var   `1`   `2`   `3`   `4`   `5`
## * <chr> <int> <int> <int> <int> <int>
## 1    V1   101   102   103   104   105
## 2    V2   106   107   108   109   110
## 3    V3   111   112   113   114   115



行方向のランキング

  • データフレームは列方向のベクトルが集合したリスト
    • 行方向には単純に関数適用できない
    • 行ごとの計算結果が列方向に格納されるので、最後に転置という考え方
# 準備:データセットの作成
X <- sample(1:15) %>% matrix(3, 5) %>% as_tibble() %>% print()
## # A tibble: 3 x 5
##      V1    V2    V3    V4    V5
##   <int> <int> <int> <int> <int>
## 1    11     1     4    10     7
## 2    14     6     8    12     3
## 3     2    15     5     9    13
# apply関数による計算
# --- 昇順なので元のデータセットを*1
# --- 行単位に計算結果が出力されるので5*3の行列になるから転置が必要
-X %>% apply(1, min_rank) %>% t()
##      V1 V2 V3 V4 V5
## [1,]  1  5  4  2  3
## [2,]  1  4  3  2  5
## [3,]  5  1  4  3  2
# {dplyr}のrowwise関数による計算
# --- rowwise()で行単位にグループ化
# --- 行単位にリストを解除してランクを作成(apply関数と同様の考え方)
X %>%
 rowwise() %>% 
 do(data.frame(-unlist(.) %>% rank() %>% t()))
## Source: local data frame [3 x 5]
## Groups: <by row>
## 
## # A tibble: 3 x 5
##      V1    V2    V3    V4    V5
## * <dbl> <dbl> <dbl> <dbl> <dbl>
## 1     1     5     4     2     3
## 2     1     4     3     2     5
## 3     5     1     4     3     2



9 データベース操作

DB接続

src

src_desc

src_df

src_local

src_memdb

src_mysql

src_postgres

src_sql

src_sqlite

src_tbls

is.src

lahman_srcs

same_src

test_register_src

DB操作

db_analyze

db_begin

db_commit

db_create_index

db_create_indexes

db_create_table

db_data_type

db_drop_table

db_explain

db_has_table

db_insert_into

db_list_tables

db_query_fields

db_query_rows

db_rollback

db_save_query

db_desc

show_query

db_write_table

SQL操作

sql

sql_build

sql_escape_ident

sql_escape_string

sql_infix

sql_join

sql_not_supported

sql_prefix

sql_quote

sql_render

sql_select

sql_semi_join

sql_set_op

sql_subquery

sql_translate_env

sql_translator

sql_variant

sql_vector

translate_sql

build_sql

is.sql

tbl_sql

join_query

query

select_query

semi_join_query

set_op_query

show_query

10 事例集

時系列データの前処理

<概要>

  • {dplyr}で操作するため時系列データをデータフレームに変換する
  • 日付データを列に追加する
    • 時系列データ操作は日付列に対して操作を行う
    • 日付データの操作を柔軟に行うため{lubridate}を活用する


<参考資料>

dplyrで時系列データの処理


<使用例>

前処理

# {dplyr}で操作するために時系列データ(xts)をデータフレームに変換
x <- sample_matrix %>% as.data.frame()

# 日付の列を追加
x$index <- sample_matrix %>% rownames() %>% as.Date()

# データセットを確認
head(x)
##                Open     High      Low    Close      index
## 2007-01-02 50.03978 50.11778 49.95041 50.11778 2007-01-02
## 2007-01-03 50.23050 50.42188 50.23050 50.39767 2007-01-03
## 2007-01-04 50.42096 50.42096 50.26414 50.33236 2007-01-04
## 2007-01-05 50.37347 50.37347 50.22103 50.33459 2007-01-05
## 2007-01-06 50.24433 50.24433 50.11121 50.18112 2007-01-06
## 2007-01-07 50.13211 50.21561 49.99185 49.99185 2007-01-07



時系列集計

# dplyrによる時系列データの処理
#  --- 元データをデータフレームにしておく
#  --- {lubridate}のmonth関数でグループ化
x %>% 
  group_by(month = month(x$index)) %>% 
  summarise(n())
## # A tibble: 6 x 2
##   month `n()`
##   <dbl> <int>
## 1     1    30
## 2     2    28
## 3     3    31
## 4     4    30
## 5     5    31
## 6     6    30



個別集計と一括集計を同時に行う

<概要>

  • 個別集計と一括集計の結果を同時に出力する場合は複文内で結果を結合する
    • 今回は個別集計にsummarise、一括集計はsummarise_atを用いる


<使用例>

2つ集計を結合して出力

# 複文内の"a"や"b"を変数として残したければ"<<-"を使う
iris %>% 
  group_by(Species) %>% {
    a <- summarise(., 'COUNT' = n())
    b <- summarise_at(., vars(starts_with("Sepal")), funs(min, max))
    inner_join(a, b, by = "Species")
  }
## # A tibble: 3 x 6
##      Species COUNT Sepal.Length_min Sepal.Width_min Sepal.Length_max
##       <fctr> <int>            <dbl>           <dbl>            <dbl>
## 1     setosa    50              4.3             2.3              5.8
## 2 versicolor    50              4.9             2.0              7.0
## 3  virginica    50              4.9             2.2              7.9
## # ... with 1 more variables: Sepal.Width_max <dbl>



参考1:summarise関数による集計

iris %>% 
  group_by(Species) %>% 
  summarise('COUNT' = n())
## # A tibble: 3 x 2
##      Species COUNT
##       <fctr> <int>
## 1     setosa    50
## 2 versicolor    50
## 3  virginica    50



参考2:summarise_at関数による集計

iris %>% 
  group_by(Species) %>% 
  summarise_at(vars(starts_with("Sepal")), funs(min, max))
## # A tibble: 3 x 5
##      Species Sepal.Length_min Sepal.Width_min Sepal.Length_max
##       <fctr>            <dbl>           <dbl>            <dbl>
## 1     setosa              4.3             2.3              5.8
## 2 versicolor              4.9             2.0              7.0
## 3  virginica              4.9             2.2              7.9
## # ... with 1 more variables: Sepal.Width_max <dbl>



条件文を集計プロセスに導入

<概要>

  • 集計処理の条件分岐は複文フラグを用いることで実現できる
  • 関数化する場合に威力を発揮する


<使用例>

if文による条件分岐

flg <- "MAX"

iris %>% 
  group_by(Species) %>% {
   if(flg == "MAX") 
      summarise(., 'MAX' = max(Sepal.Length)) 
    else 
      summarise(., 'MIN' = min(Sepal.Length))
  }
## # A tibble: 3 x 2
##      Species   MAX
##       <fctr> <dbl>
## 1     setosa   5.8
## 2 versicolor   7.0
## 3  virginica   7.9



switch文による条件分岐

flg <- "MEAN"

iris %>% 
  group_by(Species) %>% {
    switch (flg,
      "MAX"  = summarise(., 'MAX'  = max(Sepal.Length)) , 
      "MIN"  = summarise(., 'MIN'  = min(Sepal.Length)) , 
      "MEAN" = summarise(., 'MEAN' = mean(Sepal.Length))
    )
  }
## # A tibble: 3 x 2
##      Species  MEAN
##       <fctr> <dbl>
## 1     setosa 5.006
## 2 versicolor 5.936
## 3  virginica 6.588




株価を累積リターンに変換

  • 株価から累積リターンを計算する方法として期初の値で割る方法がある
# 準備:データセットの確認
X <- sample_matrix %>% as_tibble() %>% head(5)

# 累積リターンに変換
# --- 期初を1とする
X %>% 
  mutate_all(funs(./ .[1]))
## # A tibble: 5 x 4
##       Open     High      Low    Close
##      <dbl>    <dbl>    <dbl>    <dbl>
## 1 1.000000 1.000000 1.000000 1.000000
## 2 1.003811 1.006068 1.005607 1.005585
## 3 1.007617 1.006049 1.006281 1.004282
## 4 1.006668 1.005102 1.005418 1.004326
## 5 1.004088 1.002525 1.003219 1.001264



順位相関係数を一括出力

<ポイント>
・mutate_ifで数値のデータセットのみに相関係数を適用
iris %>% 
  group_by(Species) %>% 
  mutate_if(is.numeric, 
            funs(cor(., Petal.Width, method = "spearman"))) %>% 
  do(head(., 3))
## # A tibble: 9 x 5
## # Groups:   Species [3]
##   Sepal.Length Sepal.Width Petal.Length Petal.Width    Species
##          <dbl>       <dbl>        <dbl>       <dbl>     <fctr>
## 1    0.2994989   0.2865359    0.2711414           1     setosa
## 2    0.2994989   0.2865359    0.2711414           1     setosa
## 3    0.2994989   0.2865359    0.2711414           1     setosa
## 4    0.5486791   0.6599826    0.7870096           1 versicolor
## 5    0.5486791   0.6599826    0.7870096           1 versicolor
## 6    0.5486791   0.6599826    0.7870096           1 versicolor
## 7    0.3157721   0.5443098    0.3629133           1  virginica
## 8    0.3157721   0.5443098    0.3629133           1  virginica
## 9    0.3157721   0.5443098    0.3629133           1  virginica



分位列を一括追加

iris %>% 
  group_by(Species) %>% 
  mutate_if(is.numeric, funs(n(), ntile(., 5))) %>% 
  glimpse()
## Observations: 150
## Variables: 13
## $ Sepal.Length       <dbl> 5.1, 4.9, 4.7, 4.6, 5.0, 5.4, 4.6, 5.0, 4.4...
## $ Sepal.Width        <dbl> 3.5, 3.0, 3.2, 3.1, 3.6, 3.9, 3.4, 3.4, 2.9...
## $ Petal.Length       <dbl> 1.4, 1.4, 1.3, 1.5, 1.4, 1.7, 1.4, 1.5, 1.4...
## $ Petal.Width        <dbl> 0.2, 0.2, 0.2, 0.2, 0.2, 0.4, 0.3, 0.2, 0.2...
## $ Species            <fctr> setosa, setosa, setosa, setosa, setosa, se...
## $ Sepal.Length_n     <int> 50, 50, 50, 50, 50, 50, 50, 50, 50, 50, 50,...
## $ Sepal.Width_n      <int> 50, 50, 50, 50, 50, 50, 50, 50, 50, 50, 50,...
## $ Petal.Length_n     <int> 50, 50, 50, 50, 50, 50, 50, 50, 50, 50, 50,...
## $ Petal.Width_n      <int> 50, 50, 50, 50, 50, 50, 50, 50, 50, 50, 50,...
## $ Sepal.Length_ntile <int> 3, 2, 1, 1, 3, 5, 1, 3, 1, 2, 5, 2, 2, 1, 5...
## $ Sepal.Width_ntile  <int> 3, 1, 2, 1, 4, 5, 2, 3, 1, 1, 4, 3, 1, 1, 5...
## $ Petal.Length_ntile <int> 2, 2, 1, 3, 2, 5, 2, 3, 2, 3, 3, 4, 2, 1, 1...
## $ Petal.Width_ntile  <int> 1, 1, 1, 1, 1, 5, 4, 2, 2, 1, 2, 2, 1, 1, 2...



分位と全体の中央値平均

iris %>% 
  select(Species, Sepal.Length) %>% 
  group_by(Species) %>% 
  mutate(Median_all = median(Sepal.Length)) %>% 
  mutate_if(is.numeric, funs(n(), ntile(., 5))) %>% 
  mutate_if(is.numeric, funs) %>% 
  glimpse()

使途不明1

collect
compute
collapse
copy_to
inserted by FC2 system