Here’s what a basic dynasty league analysis might look like on MFL!
Set up the connection to the league:
ssb <- mfl_connect(season = 2020, league_id = 54040, rate_limit_number = 3, rate_limit_seconds = 6)
ssb
#> <MFL connection 2020_54040>
#> List of 5
#> $ platform : chr "MFL"
#> $ season : num 2020
#> $ league_id : chr "54040"
#> $ APIKEY : NULL
#> $ auth_cookie: NULL
#> - attr(*, "class")= chr "mfl_conn"
Cool! Let’s have a deeper look at what this league is like.
ssb_summary <- ff_league(ssb)
str(ssb_summary)
#> tibble [1 x 13] (S3: tbl_df/tbl/data.frame)
#> $ league_id : chr "54040"
#> $ league_name : chr "The Super Smash Bros Dynasty League"
#> $ franchise_count: num 14
#> $ qb_type : chr "1QB"
#> $ idp : logi FALSE
#> $ scoring_flags : chr "0.5_ppr, TEPrem, PP1D"
#> $ best_ball : logi TRUE
#> $ salary_cap : logi FALSE
#> $ player_copies : num 1
#> $ years_active : chr "2018-2020"
#> $ qb_count : chr "1"
#> $ roster_size : num 35
#> $ league_depth : num 490
Okay, so it’s the Smash Bros Dynasty League, it’s a 1QB league with 14 teams, best ball scoring, half ppr and point-per-first-down settings.
Let’s grab the rosters now.
ssb_rosters <- ff_rosters(ssb)
head(ssb_rosters)
#> # A tibble: 6 x 11
#> franchise_id franchise_name player_id player_name pos team age
#> <chr> <chr> <chr> <chr> <chr> <chr> <dbl>
#> 1 0001 Team Pikachu 13129 Fournette,~ RB JAC 25.6
#> 2 0001 Team Pikachu 13189 Engram, Ev~ TE NYG 25.9
#> 3 0001 Team Pikachu 11680 Landry, Ja~ WR CLE 27.7
#> 4 0001 Team Pikachu 13290 Cohen, Tar~ RB CHI 25
#> 5 0001 Team Pikachu 13155 Ross, John WR CIN 24.7
#> 6 0001 Team Pikachu 13158 Westbrook,~ WR JAC 26.7
#> # ... with 4 more variables: roster_status <chr>, drafted <chr>,
#> # draft_year <chr>, draft_round <chr>
Cool! Let’s pull in some additional context by adding DynastyProcess player values.
player_values <- dp_values("values-players.csv")
# The values are stored by fantasypros ID since that's where the data comes from.
# To join it to our rosters, we'll need playerID mappings.
player_ids <- dp_playerids() %>%
select(mfl_id,fantasypros_id)
player_values <- player_values %>%
left_join(player_ids, by = c("fp_id" = "fantasypros_id")) %>%
select(mfl_id,ecr_1qb,ecr_pos,value_1qb)
# Drilling down to just 1QB values and IDs, we'll be joining it onto rosters and don't need the extra stuff
ssb_values <- ssb_rosters %>%
left_join(player_values, by = c("player_id"="mfl_id")) %>%
arrange(franchise_id,desc(value_1qb))
head(ssb_values)
#> # A tibble: 6 x 14
#> franchise_id franchise_name player_id player_name pos team age
#> <chr> <chr> <chr> <chr> <chr> <chr> <dbl>
#> 1 0001 Team Pikachu 14803 Edwards-He~ RB KCC 21.3
#> 2 0001 Team Pikachu 13129 Fournette,~ RB JAC 25.6
#> 3 0001 Team Pikachu 11680 Landry, Ja~ WR CLE 27.7
#> 4 0001 Team Pikachu 13189 Engram, Ev~ TE NYG 25.9
#> 5 0001 Team Pikachu 14777 Burrow, Joe QB CIN 23.7
#> 6 0001 Team Pikachu 14838 Shenault, ~ WR JAC 21.8
#> # ... with 7 more variables: roster_status <chr>, drafted <chr>,
#> # draft_year <chr>, draft_round <chr>, ecr_1qb <dbl>, ecr_pos <dbl>,
#> # value_1qb <int>
Let’s do some team summaries now!
value_summary <- ssb_values %>%
group_by(franchise_id,franchise_name,pos) %>%
summarise(total_value = sum(value_1qb,na.rm = TRUE)) %>%
ungroup() %>%
group_by(franchise_id,franchise_name) %>%
mutate(team_value = sum(total_value)) %>%
ungroup() %>%
pivot_wider(names_from = pos, values_from = total_value) %>%
arrange(desc(team_value))
#> `summarise()` regrouping output by 'franchise_id', 'franchise_name' (override with `.groups` argument)
value_summary
#> # A tibble: 14 x 7
#> franchise_id franchise_name team_value QB RB TE WR
#> <chr> <chr> <int> <int> <int> <int> <int>
#> 1 0004 Team Ice Climbers 41952 567 19728 2014 19643
#> 2 0009 Team Link 38954 2852 11086 2187 22829
#> 3 0006 Team King Dedede 36827 6122 7649 1680 21376
#> 4 0007 Team Kirby 35358 3367 24013 2608 5370
#> 5 0014 Team Luigi 34025 2150 357 973 30545
#> 6 0003 Team Captain Falcon 33577 2083 10109 6223 15162
#> 7 0010 Team Yoshi 33383 1745 7596 6440 17602
#> 8 0012 Team Mewtwo 28507 1023 17510 1309 8665
#> 9 0002 Team Simon Belmont 28030 381 10792 89 16768
#> 10 0011 Team Diddy Kong 28006 1807 13287 1593 11319
#> 11 0008 Team Fox 23803 7565 9873 391 5974
#> 12 0005 Team Dr. Mario 22406 13 1355 3512 17526
#> 13 0013 Team Ness 20221 469 15726 1504 2522
#> 14 0001 Team Pikachu 19698 1303 11584 2290 4521
So with that, we’ve got a team summary of values! I like applying some context, so let’s turn these into percentages.
value_summary_pct <- value_summary %>%
mutate_at(c("team_value","QB","RB","WR","TE"),~.x/sum(.x)) %>%
mutate_at(c("team_value","QB","RB","WR","TE"),round, 3)
value_summary_pct
#> # A tibble: 14 x 7
#> franchise_id franchise_name team_value QB RB TE WR
#> <chr> <chr> <dbl> <dbl> <dbl> <dbl> <dbl>
#> 1 0004 Team Ice Climbers 0.099 0.018 0.123 0.061 0.098
#> 2 0009 Team Link 0.092 0.091 0.069 0.067 0.114
#> 3 0006 Team King Dedede 0.087 0.195 0.048 0.051 0.107
#> 4 0007 Team Kirby 0.083 0.107 0.149 0.079 0.027
#> 5 0014 Team Luigi 0.08 0.068 0.002 0.03 0.153
#> 6 0003 Team Captain Falcon 0.079 0.066 0.063 0.19 0.076
#> 7 0010 Team Yoshi 0.079 0.055 0.047 0.196 0.088
#> 8 0012 Team Mewtwo 0.067 0.033 0.109 0.04 0.043
#> 9 0002 Team Simon Belmont 0.066 0.012 0.067 0.003 0.084
#> 10 0011 Team Diddy Kong 0.066 0.057 0.083 0.049 0.057
#> 11 0008 Team Fox 0.056 0.241 0.061 0.012 0.03
#> 12 0005 Team Dr. Mario 0.053 0 0.008 0.107 0.088
#> 13 0013 Team Ness 0.048 0.015 0.098 0.046 0.013
#> 14 0001 Team Pikachu 0.046 0.041 0.072 0.07 0.023
Armed with a value summary like this, we can see team strengths and weaknesses pretty quickly, and figure out who might be interested in your positional surpluses and who might have a surplus at a position you want to look at.
Another question you might ask: what is the average age of any given team?
I like looking at average age by position, but weighted by dynasty value. This helps give a better idea of age for each team!
age_summary <- ssb_values %>%
group_by(franchise_id,pos) %>%
mutate(position_value = sum(value_1qb,na.rm=TRUE)) %>%
ungroup() %>%
mutate(weighted_age = age*value_1qb/position_value) %>%
group_by(franchise_id,franchise_name,pos) %>%
summarise(count = n(),
age = sum(weighted_age,na.rm = TRUE)) %>%
pivot_wider(names_from = pos,
values_from = c(age,count))
#> `summarise()` regrouping output by 'franchise_id', 'franchise_name' (override with `.groups` argument)
age_summary
#> # A tibble: 14 x 10
#> # Groups: franchise_id, franchise_name [14]
#> franchise_id franchise_name age_QB age_RB age_TE age_WR count_QB count_RB
#> <chr> <chr> <dbl> <dbl> <dbl> <dbl> <int> <int>
#> 1 0001 Team Pikachu 24.2 23.0 25.9 26.4 6 6
#> 2 0002 Team Simon Be~ 34.4 23.9 24.1 24.3 7 10
#> 3 0003 Team Captain ~ 24.7 23.7 30.1 26.4 6 11
#> 4 0004 Team Ice Clim~ 27.6 24.6 26.1 27.8 5 7
#> 5 0005 Team Dr. Mario 37.7 19.4 23.9 24.4 3 7
#> 6 0006 Team King Ded~ 24.8 25.5 25.8 24.8 3 10
#> 7 0007 Team Kirby 23.9 24.1 29.4 26.0 3 11
#> 8 0008 Team Fox 24.7 26.1 26.0 26.7 3 11
#> 9 0009 Team Link 25.8 25.8 27.1 27.4 2 9
#> 10 0010 Team Yoshi 28.9 21.4 26.8 24.2 4 4
#> 11 0011 Team Diddy Ko~ 30.7 25.4 23.6 25.4 2 13
#> 12 0012 Team Mewtwo 29.3 24.1 24.5 23.5 4 6
#> 13 0013 Team Ness 30.6 23.1 22.8 26.1 5 9
#> 14 0014 Team Luigi 32.0 28.2 26.9 26.5 5 9
#> # ... with 2 more variables: count_TE <int>, count_WR <int>