Nhân dịp này optim
sẽ không làm việc rõ ràng bởi vì bạn có những hạn chế bình đẳng. constrOptim
sẽ không hoạt động hoặc vì cùng một lý do (tôi đã thử chuyển đổi bình đẳng thành hai sự bất bình đẳng nghĩa là lớn hơn và nhỏ hơn 15 nhưng điều này không hoạt động với constrOptim
).
Tuy nhiên, có một gói phần mềm dành riêng cho loại vấn đề và đó là Rsolnp
.
Bạn sử dụng nó theo cách sau:
#specify your function
opt_func <- function(x) {
10 - 5*x[1] + 2 * x[2] - x[3]
}
#specify the equality function. The number 15 (to which the function is equal)
#is specified as an additional argument
equal <- function(x) {
x[1] + x[2] + x[3]
}
#the optimiser - minimises by default
solnp(c(5,5,5), #starting values (random - obviously need to be positive and sum to 15)
opt_func, #function to optimise
eqfun=equal, #equality function
eqB=15, #the equality constraint
LB=c(0,0,0), #lower bound for parameters i.e. greater than zero
UB=c(100,100,100)) #upper bound for parameters (I just chose 100 randomly)
Output:
> solnp(c(5,5,5),
+ opt_func,
+ eqfun=equal,
+ eqB=15,
+ LB=c(0,0,0),
+ UB=c(100,100,100))
Iter: 1 fn: -65.0000 Pars: 14.99999993134 0.00000002235 0.00000004632
Iter: 2 fn: -65.0000 Pars: 14.999999973563 0.000000005745 0.000000020692
solnp--> Completed in 2 iterations
$pars
[1] 1.500000e+01 5.745236e-09 2.069192e-08
$convergence
[1] 0
$values
[1] -10 -65 -65
$lagrange
[,1]
[1,] -5
$hessian
[,1] [,2] [,3]
[1,] 121313076 121313076 121313076
[2,] 121313076 121313076 121313076
[3,] 121313076 121313076 121313076
$ineqx0
NULL
$nfuneval
[1] 126
$outer.iter
[1] 2
$elapsed
Time difference of 0.1770101 secs
$vscale
[1] 6.5e+01 1.0e-08 1.0e+00 1.0e+00 1.0e+00
Vì vậy, các giá trị tối ưu kết quả là:
$pars
[1] 1.500000e+01 5.745236e-09 2.069192e-08
có nghĩa là tham số đầu tiên là 15 và phần còn lại bằng không và không. Đây thực sự là mức tối thiểu toàn cầu trong hàm của bạn kể từ khi x2 được thêm vào hàm và 5 * x1 có ảnh hưởng lớn hơn nhiều (âm) so với x3 trên kết quả. Sự lựa chọn của 15, 0, 0 là giải pháp và tối thiểu toàn cầu cho hàm theo các ràng buộc.
Chức năng hoạt động tuyệt vời!
Đẹp nhất! Khi OP nói: "Đây là một ví dụ đơn giản về vấn đề thực sự" nó làm cho tôi nghĩ rằng vấn đề thực tế có thể là phi tuyến. Vì vậy, chỉ để chắc chắn tôi đề nghị một phương pháp phi tuyến (mà hoạt động anyway ngay cả khi nó là chậm hơn). Cung cấp gradient (đơn giản cho trường hợp này) làm cho nó thậm chí còn nhanh hơn nếu tốc độ là một vấn đề. Dù sao, tôi không có ý xấu, nó thực sự là tốt mà bạn thêm câu trả lời này, chắc chắn hữu ích. – LyzandeR