JavaScriptを有効にしてください

CasADiのOptiスタックでcallback関数を使って解の推移を取得する

 ·   4 min read

※記事内に商品プロモーションを含むことがあります。

はじめに

最適化フレームワークCasADiのOptiスタックでcallback関数を使って、最適化ソルバの各反復における解の推移を取得する方法をまとめました。言語はPythonです。

検証環境は以下の通りです。

ソフトウェア バージョン
Python 3.9.7
CasADi 3.6.3

callback関数の基本的な使い方

2変数の凸連続最適化問題を例に、Optiスタックでcallback関数を使用する例を以下に示します。最適化ソルバには、凸連続最適化問題に適したIPOPTを使用しています。

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
import casadi as ca

opti = ca.Opti()

# 変数を定義
x1 = opti.variable()
x2 = opti.variable()

# 初期値を指定
opti.set_initial(x1, 100)
opti.set_initial(x2, 10)

# 目的関数を定義
obj = x1**2 + x2**2
opti.minimize(obj)

# 制約条件を定義
opti.subject_to( x1*x2 >= 1 )

# 最適化ソルバを設定
p_opts = {}
s_opts = {'print_level': 4}
opti.solver('ipopt', p_opts, s_opts)

# callback関数を定義
opti.callback(lambda i: print(i, opti.debug.value(x1)))

# 最適化計算を実行
sol = opti.solve()

上記のコードを実行すると、変数x1, x2の内、x1の推移が以下のようにコンソールに出力されます。左側の数字は最適化ソルバの反復回数、右側の数字はx1です。x1が初期値の100から、最適解の1に近づいていることが分かります。

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
0 100.0
1 4.689542724520109
2 1.0795374935431634
3 0.5517089519112491
4 0.8179977199977577
5 1.0262185402295063
6 1.0018147643511712
7 1.0000773780870829
8 1.00000092044001
9 0.999999996253379
1
opti.callback(lambda i: print(i, opti.debug.value(x1)))

上記の例では、ラムダ式(無名関数)を使い、最適化ソルバの反復ごとに呼び出すcallback関数を定義しています。このラムダ式の引数iには、反復回数が与えられます。また、変数にはopti.debug.value()メソッドを使ってアクセスします。

全変数の推移を取得

全ての変数の推移を取得する方法は色々ありますが、1例を以下に示します。logというリストに各反復のopti.debugを追加していきます。最適化計算の終了後、各変数を取り出します。

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
log = []

# callback関数を定義
opti.callback(lambda i: log.append(opti.debug))

# 最適化計算を実行
sol = opti.solve()

for deb in log:
    print(deb.value(x1), deb.value(x2))

実行結果

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
100.0 10.0
4.689542724520109 16.043123296985808
1.0795374935431634 1.9311817025775309
0.5517089519112491 0.6966250709025741
0.8179977199977577 0.8500586577938801
1.0262185402295063 1.0243870906377914
1.0018147643511712 1.0017967248568909
1.0000773780870829 1.000077373885306
1.00000092044001 1.0000009204400082
0.999999996253379 0.999999996253379

参考

CasADiの公式リファレンス
CasADi - Docs

シェアする

Helve
WRITTEN BY
Helve
関西在住、電機メーカ勤務のエンジニア。X(旧Twitter)で新着記事を配信中です

サイト内検索