属性资产,以最小化R中的方差

时间:2017-11-24 14:51:53

标签: r mathematical-optimization

我有一个要解决的优化问题。以下是上下文:我可以购买广告来播放潜在的“屏幕”。每个屏幕都有一个名为“grp”的值。问题是,我有不同的电影,我想要做的是尽量减少每部电影的总grp差异。

我有一个约束:所有屏幕都必须归功于一部电影。

以下是可用屏幕列表的示例:

    date     channel    screen_id format grp
    <dttm>     <chr>        <chr>  <chr> <dbl>
1 2017-10-08 channel A      2142 *  45s  9.95
2 2017-10-08 channel A      2391 T  30s  1.43
3 2017-10-09 channel A      2320 S  20s  2.60
4 2017-10-09 channel A      2410 S  20s  1.03
5 2017-10-09 channel A      2430 S  20s  0.78
6 2017-10-10 channel A      1903 S  20s  2.70

我有三部不同的电影,让我们称之为c("film_A", "film_B", "film_C"),我想确保最小化每部电影的总grp差异。

预期输出(此处属性是随机的,因此未进行优化):

        date   channel screen_id format   grp   film
      <dttm>     <chr>     <chr>  <chr> <dbl>  <chr>
1 2017-10-08 channel A      2142 *  45s  9.95 film_a
2 2017-10-08 channel A      2391 T  30s  1.43 film_b
3 2017-10-09 channel A      2320 S  20s  2.60 film_c
4 2017-10-09 channel A      2410 S  20s  1.03 film_a
5 2017-10-09 channel A      2430 S  20s  0.78 film_b
6 2017-10-10 channel A      1903 S  20s  2.70 film_c

在这种情况下,每部胶片的总grp具有很大的差异:

    film grp_per_film
   <chr>        <dbl>
1 film_a        16.45
2 film_b         3.78
3 film_c         6.50

我想要最小化的是电影的总grp的变化,而不是每部电影中屏幕的grp变化。

我有点卡在这个上面。我查看了PortfoliAnalytics包,但我无法将组合逻辑应用于此问题。

1 个答案:

答案 0 :(得分:0)

以下是使用kmeans可以执行的操作。基本上,kmeans创建3个grp集群。这确实可以最小化集群之间grps的差异。

dt <- read.table(text="
date       channel       screen_id format grp
2017-10-08 'channel A'      '2142 '  45s  9.95
2017-10-08 'channel A'     '2391 T'  30s  1.43
2017-10-09 'channel A'      '2320 S'  20s  2.60
2017-10-09 'channel A'      '2410 S'  20s  1.03
2017-10-09 'channel A'      '2430 S'  20s  0.78
2017-10-10 'channel A'      '1903 S'  20s  2.702",header=TRUE, stringsAsFactors=FALSE)

dt$film <- kmeans(dt$grp,centers=3)$cluster

        date   channel screen_id format   grp film
1 2017-10-08 channel A     2142     45s 9.950    2
2 2017-10-08 channel A    2391 T    30s 1.430    1
3 2017-10-09 channel A    2320 S    20s 2.600    3
4 2017-10-09 channel A    2410 S    20s 1.030    1
5 2017-10-09 channel A    2430 S    20s 0.780    1
6 2017-10-10 channel A    1903 S    20s 2.702    3

如果你想使用data.table(按日期或星期分组可能有用),这可行:

library(data.table)
setDT(dt)
dt[,film:=kmeans(grp,centers=3)$cluster]

         date   channel screen_id format   grp film
1: 2017-10-08 channel A     2142     45s 9.950    2
2: 2017-10-08 channel A    2391 T    30s 1.430    1
3: 2017-10-09 channel A    2320 S    20s 2.600    3
4: 2017-10-09 channel A    2410 S    20s 1.030    1
5: 2017-10-09 channel A    2430 S    20s 0.780    1
6: 2017-10-10 channel A    1903 S    20s 2.702    3