autodiff=true
)와
Optim.jl
를 사용하여 다음 주어진 함수 (
quad_function
를) 최적화 (최소화) 좋아
에 대한 autodiff`와 비용 함수를 최적화 할 수 있습니다.줄리아 :`Optim.jl`와`정수
내 목적 함수 은 정수로Real
값을 반올림하므로 단계적입니다. 나는 autodiff
옵션을 사용할 때
, 내 Real
값은 dual numbers (ForwardDiff.Dual
들)을 얻는다. 그러나 불행하게도 ForwardDiff.Dual
유형에 대해 구현 된 round
함수가 없습니다. 따라서 나는 실제 부품을 추출하는 roundtoint64
함수를 작성했습니다. 이 접근법은 최적화하는 동안 문제를 일으 킵니다.
문제 인 optimize
기능을 즉시 수렴 및 진행되지 않습니다 :
using Plots
plotlyjs()
function roundtoint64(x)
if typeof(x) <: ForwardDiff.Dual
roundtoint64(x.value)
else
Int64(round(x))
end
end
function quad_function(xs::Vector)
roundtoint64(xs[1])^2 + roundtoint64(xs[2])^2
end
x, y = linspace(-5, 5, 100), linspace(-5, 5, 100)
z = Surface((x,y)->quad_function([x,y]), x, y)
surface(x,y,z, linealpha = 0.3)
이처럼 내 quad_function
보이는 방법이다.
using Optim
res = Optim.optimize(
quad_function,
[5.0,5.0],
Newton(),
OptimizationOptions(
autodiff = true,
# show_trace = true
))
결과 : 나는 또한 반올림 것을 피하기 위해 정수 [5,5]
의 벡터와 optimize
기능을 초기화하려고했으나 그에서 초기 단계의 크기를 찾아도 문제가 발생
Results of Optimization Algorithm
* Algorithm: Newton's Method
* Starting Point: [5.0,5.0]
* Minimizer: [5.0,5.0]
* Minimum: 5.000000e+01
* Iterations: 0
* Convergence: true
* |x - x'| < 1.0e-32: false
* |f(x) - f(x')|/|f(x)| < 1.0e-32: false
* |g(x)| < 1.0e-08: true
* Reached Maximum Number of Iterations: false
* Objective Function Calls: 1
* Gradient Calls: 1
optimal_values = Optim.minimizer(res) # [5.0, 5.0]
optimum = Optim.minimum(res) # 50.0
:
ERROR: InexactError()
in alphainit(::Int64, ::Array{Int64,1}, ::Array{Int64,1}, ::Int64) at /home/sebastian/.julia/v0.5/Optim/src/linesearch/hz_linesearch.jl:63
in optimize(::Optim.TwiceDifferentiableFunction, ::Array{Int64,1}, ::Optim.Newton, ::Optim.OptimizationOptions{Void}) at /home/sebastian/.julia/v0.5/Optim/src/newton.jl:69
in optimize(::Function, ::Array{Int64,1}, ::Optim.Newton, ::Optim.OptimizationOptions{Void}) at /home/sebastian/.julia/v0.5/Optim/src/optimize.jl:169
질문 :optimize
에게 전자로만 알려줄 수 있습니까? xplore 정수 공간?
업데이트 : 내가 Int64
로 변환하는 방법에 문제가 내가 더 이상 파생 상품/그라디언트를 계산할 수 없습니다, 따라서 ForwardDiff.Dual
의이없고 있다고 생각합니다. 더 좋은 round
함수는 어떻게 중첩 된 이중을 반올림하고 이중을 돌려주는 것처럼 보이게 할 수 있습니까?
그래디언트가 0이므로 알고리즘이 중지됩니다. 당신의 문제는 매끄러운 기능을 기대하는 솔버에게는 적합하지 않습니다. 함수에 MIQP (mixed integer quadratic programming) 솔버와 같은 것을 사용해보십시오. –
@ErwinKalvelagen 감사합니다. 그러나 솔버가 적합하지 않다면 일반적으로이 매핑을 수행하는 방법이 있다고 생각합니까? 왜냐하면 그것은 내 persperctive에서 부드러운 함수로부터 멀지 않은 것이기 때문에 ... – swiesend
그것은 전혀 부드럽 지 않다. 그리고 지역 nlp 솔버가 멈추기로 결정할 0 그라디언트가있는이 모든 영역을 가지고있다. 이것은 근본적으로 분리 된 문제에 대한 잘못된 기술입니다. –