首页 > 解决方案 > 在 R 中优化数据框

问题描述

嗨,我有这个数据集:

> structure(list(leng = c(100, 200, 300, 400, 500, 600, 700, 800, 
900, 1000, 100, 200, 300, 400, 500, 600, 700, 800, 900, 1000, 
100, 200, 300, 400, 500, 600, 700, 800, 900, 1000, 100, 200, 
300, 400, 500, 600, 700, 800, 900, 1000, 100, 200, 300, 400, 
500, 600, 700, 800, 900, 1000, 100, 200, 300, 400, 500, 600, 
700, 800, 900, 1000, 100, 200, 300, 400, 500, 600, 700, 800, 
900, 1000, 100, 200, 300, 400, 500, 600, 700, 800, 900, 1000, 
100, 200, 300, 400, 500, 600, 700, 800, 900, 1000, 100, 200, 
300, 400, 500, 600, 700, 800, 900, 1000, 100, 200, 300, 400, 
500, 600, 700, 800, 900, 1000, 100, 200, 300, 400, 500, 600, 
700, 800, 900, 1000, 100, 200, 300, 400, 500, 600, 700, 800, 
900, 1000, 100, 200, 300, 400, 500, 600, 700, 800, 900, 1000, 
100, 200, 300, 400, 500, 600, 700, 800, 900, 1000, 100, 200, 
300, 400, 500, 600, 700, 800, 900, 1000, 100, 200, 300, 400, 
500, 600, 700, 800, 900, 1000, 100, 200, 300, 400, 500, 600, 
700, 800, 900, 1000, 100, 200, 300, 400, 500, 600, 700, 800, 
900, 1000, 100, 200, 300, 400, 500, 600, 700, 800, 900, 1000), 
    flow = c(10, 10, 10, 10, 10, 10, 10, 10, 10, 10, 20, 20, 
    20, 20, 20, 20, 20, 20, 20, 20, 30, 30, 30, 30, 30, 30, 30, 
    30, 30, 30, 40, 40, 40, 40, 40, 40, 40, 40, 40, 40, 50, 50, 
    50, 50, 50, 50, 50, 50, 50, 50, 60, 60, 60, 60, 60, 60, 60, 
    60, 60, 60, 70, 70, 70, 70, 70, 70, 70, 70, 70, 70, 80, 80, 
    80, 80, 80, 80, 80, 80, 80, 80, 90, 90, 90, 90, 90, 90, 90, 
    90, 90, 90, 100, 100, 100, 100, 100, 100, 100, 100, 100, 
    100, 110, 110, 110, 110, 110, 110, 110, 110, 110, 110, 120, 
    120, 120, 120, 120, 120, 120, 120, 120, 120, 130, 130, 130, 
    130, 130, 130, 130, 130, 130, 130, 140, 140, 140, 140, 140, 
    140, 140, 140, 140, 140, 150, 150, 150, 150, 150, 150, 150, 
    150, 150, 150, 160, 160, 160, 160, 160, 160, 160, 160, 160, 
    160, 170, 170, 170, 170, 170, 170, 170, 170, 170, 170, 180, 
    180, 180, 180, 180, 180, 180, 180, 180, 180, 190, 190, 190, 
    190, 190, 190, 190, 190, 190, 190, 200, 200, 200, 200, 200, 
    200, 200, 200, 200, 200), diam = c(2, 2, 2, 2, 2, 2, 2, 2, 
    2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 
    2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 
    2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 
    2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 
    2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 
    2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 
    2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 
    2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 
    2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 
    2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 
    2, 2)), out.attrs = list(dim = c(leng = 10L, flow = 20L, 
diam = 1L), dimnames = list(leng = c("leng= 100", "leng= 200", 
"leng= 300", "leng= 400", "leng= 500", "leng= 600", "leng= 700", 
"leng= 800", "leng= 900", "leng=1000"), flow = c("flow= 10", 
"flow= 20", "flow= 30", "flow= 40", "flow= 50", "flow= 60", "flow= 70", 
"flow= 80", "flow= 90", "flow=100", "flow=110", "flow=120", "flow=130", 
"flow=140", "flow=150", "flow=160", "flow=170", "flow=180", "flow=190", 
"flow=200"), diam = "diam=2")), class = "data.frame", row.names = c(NA, 
-200L))

而这个功能

> hazwil2= function(diam,flow,leng){
psi2=((1/(2.31*100))*1050*((flow/140)^1.852)*leng*diam^-4.87)
return(psi2)
}

我试图通过改变直径的值来使用优化来最小化 psi2。psi2 应该小于 3,它不必为零。

这有效:

> optimize(f=hazwil2,interval=c(0.1,12),flow=100,leng=400)

但是当我尝试在流和长度的向量上运行优化函数时,如下所示:

> optimize(f=hazwil2,interval=c(0.1,12),flow=df2$flow,leng=df2$leng)

我得到:

“优化”中的无效函数值

我尝试使用 apply() 但这似乎也不起作用。任何帮助是极大的赞赏!

格里

标签: roptimization

解决方案


我们可以使用data.table来解决这个问题:

# load library
require(data.table)

# convert data.frame to data.table
setDT(df2)

# create an id column (it will be later removed)
df2[, id := 1:.N]

# Estimate and assign the minimum (output 1 of optimize) 
#      for each flow and leng values:
df2[, minimum := optimize(hazwil2, 
                          interval = c(0.1, 12), 
                          flow, 
                          leng)[[1]], 
       by = id]

# Estimate and assing objective (output 2 of optimize)
#             for each pair of flow and leng:
df2[, objective := optimize(hazwil2, 
                            interval = c(0.1, 12), 
                            flow, 
                            leng)[[2]], 
      by = id]

# remove id column
df2[, id := NULL]

# view df2:
> df2
     leng flow diam  minimum    objective
  1:  100   10    2 11.99994 1.902594e-05
  2:  200   10    2 11.99994 3.805188e-05
  3:  300   10    2 11.99994 5.707782e-05
  4:  400   10    2 11.99994 7.610376e-05
  5:  500   10    2 11.99994 9.512970e-05
 ---                                     
196:  600  200    2 11.99994 2.930926e-02
197:  700  200    2 11.99994 3.419414e-02
198:  800  200    2 11.99994 3.907902e-02
199:  900  200    2 11.99994 4.396390e-02
200: 1000  200    2 11.99994 4.884877e-02

推荐阅读