从每日数据的DataFrame绘制每周数据

从每日数据的DataFrame绘制每周数据,dataframe,julia,Dataframe,Julia,我有一个Julia数据帧,如下所示: │ Row │ date │ users │ posts │ topics │ likes │ pageviews │ │ │ Date │ Int64 │ Int64 │ Int64 │ Int64 │ Int64 │ ├──────┼────────────────────┼───────┼───────┼────────┼───────┼───────────┤ │ 1

我有一个Julia数据帧,如下所示:

│ Row  │ date               │ users │ posts │ topics │ likes │ pageviews │
│      │ Date               │ Int64 │ Int64 │ Int64  │ Int64 │ Int64     │
├──────┼────────────────────┼───────┼───────┼────────┼───────┼───────────┤
│ 1    │ Date("2020-06-16") │  1    │  3    │ 4      │ 7     │ 10000     │
│ 2    │ Date("2020-06-15") │  2    │  2    │ 5      │ 8     │ 20000     │
│ 3    │ Date("2020-06-14") │  3    │  3    │ 6      │ 9     │ 30000     │
我想要一个帖子和日期的对比图,但是每天的数据太吵了,所以我想 你想把每周的帖子加起来,然后画出来吗?最简单的是什么
实现这一目标的途径

TimeSeries包提供了各种实用程序来处理TimeSeries数据。 在这种情况下,您可以使用
折叠
将每日数据转换为每周数据:

julia> using TimeSeries, DataFrames

julia> ta = TimeArray(df.date, df.posts)
1311×1 TimeArray{Int64,1,Date,Array{Int64,1}} 2016-10-19 to 2020-06-16
│            │ A     │
├────────────┼───────┤
│ 2016-10-19 │ 1     │
│ 2016-10-20 │ 2     │
│ 2016-10-21 │ 3     │
│ 2016-10-23 │ 4     │
...

julia> weekly = collapse(ta, week, last, sum)
192×1 TimeArray{Int64,1,Date,Array{Int64,1}} 2016-10-23 to 2020-06-16
│            │ A     │
├────────────┼───────┤
│ 2016-10-23 │ 10    │
│ 2016-10-28 │ 22    │
│ 2016-11-06 │ 34    │
...

julia> using Gadfly
julia> plot(DataFrame(weekly)[1:end-1,:], x=:timestamp, y=:A, Geom.line(), Guide.ylabel("Weekly sum of Posts"), Guide.xlabel("Week"))

在数据帧中,您可以将
groupby
combine
结合使用,如下所示:

julia> using Statistics, Dates, Pipe;
julia> df = DataFrame(date = range(Date(2000, 01, 01), Date(2020, 01, 01), step = Day(1)));
julia> df.val = rand(nrow(df));
julia> @pipe df |>
           transform(_,
               :date => ByRow(year) => :year,
               :date => ByRow(week) => :week # 1:52
           ) |>
           groupby(_, [:week, :year]) |>
           transform(_, :val => mean)
如果想要移动平均线,可以使用以下函数

julia> function lagged_mean(x, b)
           map(1:length(x)) do i
               i < b ? missing : mean(@view x[i-b+1:i])
           end
       end

julia> lagged_mean(df.val, 7)

julia>函数滞后平均值(x,b)
地图(1:长度(x))我该怎么办
我滞后平均值(df.val,7)

这是我的建议,它允许控制您使用哪一天作为一周的开始日期(我在这里使用星期一),并且对丢失的数据也很可靠(数据集中可以重复日期):

请注意,与每周使用<代码>相比,性能提高了3.5倍:

julia> @btime transform($df,:date => (d->floor.(d,Week)) => :week);
  63.699 μs (68 allocations: 175.47 KiB)
julia> @btime transform($df,:date => (d->Dates.days.(d .- Date(2000, 1, 3)) .÷ 7) => :week);
  18.900 μs (74 allocations: 175.64 KiB)

在这里,你如何控制一周的开始日期?利用地板不是更好吗<代码>使用日期;dfw=转换(df,:日期=>(d->楼层(d,周))=>:周);combine(groupby(dfw,:week),:pageviews=>sum)周日(日本)或周六(中东)如何开始一周?这也比我在i7-10710U CPU上使用Julia 1.4.2编写的代码(请参见我的编辑)慢3.5倍,根本没有性能差异。我在运行i7-10510U的Julia 1.5.0 beta1上测试了genauguy示例中的数据帧窗口。你的数据框有多大?它很小(3行),但在Linux下。
julia> @btime transform($df,:date => (d->floor.(d,Week)) => :week);
  63.699 μs (68 allocations: 175.47 KiB)
julia> @btime transform($df,:date => (d->Dates.days.(d .- Date(2000, 1, 3)) .÷ 7) => :week);
  18.900 μs (74 allocations: 175.64 KiB)