用 Chain.jl 提升可读性

Julia 中的数据操作

Katerina Zahradova

Instructor

复杂代码的问题

# 不易读
combine(groupby(
    select(wages, :year, :eff_2020)
        :year),
        :eff_2020 => mean)
# 很容易忘记一个括号
combine(groupby(wages, :year, ... )
syntax: incomplete: 
输入过早结束 ...
# 过多的中间变量
w_tmp = select(wages, :state, :year, :eff_2020)
year_groups = groupby(w_tmp, :year)
combine(year_groups, :eff_2020 => mean)
# 容易覆盖重要数据
select!(wages, :year, :eff_2020)
groupby(wages, :state)
ArgumentError: 
未找到列名 "state" ...
Julia 中的数据操作

什么是管道?

  • 编码思路
  • 将多个连续函数调用串联
  • 代码更易读
  • 无需保存中间结果
  • 无需嵌套

管道

Julia 中的数据操作

使用 Chain.jl

按年份计算平均最低工资

  • 选择所需列
  • :year 对 DataFrame 分组
  • 计算每年的平均值
@chain wages begin

select(:state, :year, :eff_2020)
groupby(:year) combine(:eff_2020 => mean)
end
53×2 DataFrame
Row    year    eff_2020_mean
       Int64   Float64
_________________________
1      1968    9.28529
...
Julia 中的数据操作

用 _ 进行管道传递

@chain wages begin
    select(:state, :year, :eff_2020)
    groupby(:year)
    combine(:eff_2020 => mean)    

# 在多处用 _ 传递管道值 plot(_.year, _.eff_2020_mean)
end

各年份的实际最低工资图

Julia 中的数据操作

用 @aside 跳过管道

@chain wages begin
    select(:state, :year,
        :eff_2020, :state_2020)
    groupby(:year)
    combine([:eff_2020,
        :state_2020] .=> mean)

# 用 @aside 跳过管道 @aside plot(_.year,_.eff_2020_mean) plot!(_.year,_.state_2020_mean)
end

州工资与最低工资对比图

Julia 中的数据操作

保存结果

# 将链式宏的输出保存为变量
wages_mean_by_year = @chain wages begin
    select(:state, :year, :eff_2020, :state_2020)
    groupby(:year)
    combine([:eff_2020, :state_2020] .=> mean)
end
# 打印第一行
println(first(wages_mean_by_year))
DataFrameRow
Row | year     eff_2020_mean   state_2020_mean
    | Int64    Float64         Float64
____|_________________________________
   1| 1968     9.28529         6.21549
Julia 中的数据操作

让我们来练习!

Julia 中的数据操作

Preparing Video For Download...