私の備忘録がないわね...私の...

画像処理とかプログラミングのお話。

matplotlibで日本語とLaTeX(LuaTeX)を共存させる

TL;DR

apt-get update
apt-get install -y \
texlive \
texlive-latex-extra \
texlive-fonts-recommended \
dvipng \
cm-super

apt update
apt install -y \
texlive-luatex \
texlive-lang-japanese
import matplotlib as mpl
import matplotlib.pyplot as plt
import japanize_matplotlib

mpl.use('pgf')
plt.rcParams['text.usetex'] = True
plt.rcParams['pgf.texsystem'] = 'lualatex'

詳細な手順

matplotlib上で日本語とLaTeXを同時に使う方法を書き残します. 厳密にはLuaTexです. 後述の通り, PGFバックエンドを用いるので, plt.show()などで期待されるインタラクティブな画像表示は機能しません. 画像を保存するだけで十分な方に向けた記事です.

各versionは以下の通りです.

  • Python 3.8.13
  • matplotlib 3.6.2
  • japanize-matplotlib 1.1.3

LaTeX環境は以下のように構築されています.

apt-get install texlive texlive-latex-extra texlive-fonts-recommended dvipng cm-super
pip3 install latex

matplotlibで日本語を使う方法にjapanize-matplotlibがあります. これは以下のようなコードを実行する分には何の問題もありません。

import matplotlib.pyplot as plt
import japanize_matplotlib

plt.title('タイトル')
plt.show()

しかし以下のようにLaTeXと同時に使おうとするとエラーが起きます. これは特殊な設定をしないとLaTeXで日本語が使えないことに由来します.

import matplotlib.pyplot as plt
import japanize_matplotlib

plt.rcParams['text.usetex'] = True
plt.title('タイトル')
plt.show()
RuntimeError: latex was not able to process the following string:
b'\\u30bf\\u30a4\\u30c8\\u30eb'
...
! Package inputenc Error: Unicode character タ (U+30BF)
(inputenc)                not set up for use with LaTeX.
...
l.29 {\rmfamily タ
                   イトル}%

これは, 基本的にLaTeXで日本語を使えるようにすれば解消されます. ここでは一例としてLuaTeXtexlive-lang-japaneseを使う方法を示します.

texlive-luatextexlive-lang-japaneseをインストールします.

apt update
apt install -y texlive-luatex texlive-lang-japanese

コードは以下のように変更します.

import matplotlib as mpl
import matplotlib.pyplot as plt
import japanize_matplotlib

mpl.use('pgf')
plt.rcParams['text.usetex'] = True
plt.rcParams['pgf.texsystem'] = 'lualatex'
plt.title('タイトル')
# plt.show()
plt.savefig('title.pdf')

PGFバックエンドを用いるので, plt.show()などで期待されるインタラクティブな画像表示は機能しません.

matplotlibでbmやboldsymbolを使う

各versionは以下の通り.

  • Python 3.8.13
  • matplotlib 3.6.2

Latex環境の構築

apt-get install texlive texlive-latex-extra texlive-fonts-recommended dvipng cm-super
pip3 install latex

bmを使う場合のコード例.

import matplotlib.pyplot as plt

plt.rcParams['text.usetex'] = True
plt.rc('text.latex', preamble=r'\usepackage{bm}')

plt.title(r'Bold $\bm{A}$')

boldsymbolを使う場合のコード例.

import matplotlib.pyplot as plt

plt.rcParams['text.usetex'] = True
plt.rc('text.latex', preamble=r'\usepackage{amsmath}')

plt.title(r'Bold $\boldsymbol{A}$')

CUDA と PyTorch 公式 Docker Image の相性が悪いとき

PyTorch で GPU を扱うとき, PyTorch 公式 Docker Image を使用しているかもしれません.

FROM pytorch/pytorch:1.9.1-cuda11.1-cudnn8-devel

ほとんどの場合, 大丈夫なのですが, 稀に以下のエラーに遭遇することがあります.

docker: Error response from daemon: OCI runtime create failed: container_linux.go:380: starting container process caused: process_linux.go:545: container init caused: Running hook #0:: error running hook: exit status 1, stdout: , stderr: nvidia-container-cli: requirement error: unsatisfied condition: cuda>=11.1, please update your driver to a newer version, or use an earlier cuda container: unknown.

これは PyTorch 公式 Image ではなく, NVIDIA 公式 Image を使うと直るかもしれません.

FROM nvcr.io/nvidia/pytorch:21.06-py3

点と超平面の最小 lp 距離

「点と直線の距離」やその多次元拡張である「点と超平面の距離」は高校数学的な解法, 例えば連立方程式やベクトルで解くことが出来るポピュラーな問題設定です. 本記事は更に拡張した「点と超平面の最小  l_p 距離」について考えます. 通常良く使われる  l_2 距離では法線ベクトルを使った解法が有名ですが, これは全ての  p に対しては成り立ちません. なぜなら距離を最小にする方向が法線ベクトルとは限らないからです.

改めて, 問題設定を確認します. 点を  \boldsymbol{x}_0 \in \mathbb{R}^n, 超平面を  \boldsymbol{a}^\top\boldsymbol{x} + a_0 = 0 とすると, 今回の問題は以下の最小化問題によって記述できます.

 \displaystyle
\min_{\boldsymbol{x}} \| \boldsymbol{x} \|_p \quad \text{s.t.} \quad \boldsymbol{a}^\top (\boldsymbol{x}_0 + \boldsymbol{x}) + a_0 = 0.

この問題は  a_0 \leftarrow \boldsymbol{a}^\top \boldsymbol{x}_0 + a_0 とすれば, 以下の最小化問題と等価です. これは  \boldsymbol{x}_0 が原点になるような平行移動です.

 \displaystyle
\min_{\boldsymbol{x}} \| \boldsymbol{x} \|_p \quad \text{s.t.} \quad \boldsymbol{a}^\top \boldsymbol{x} + a_0 = 0.

さらに  l_p 距離の定義からこの最小化問題は以下の最小化問題と解が同じです. 下の形の方がラグランジュの未定乗数法で解くとき簡単です. 特に微分後の形が簡単になります.

 \displaystyle
\min_{\boldsymbol{x}} \sum_{i=1}^n | x_i |^p \quad \text{s.t.} \quad \boldsymbol{a}^\top\boldsymbol{x} + a_0 = 0.

解法 1 (そのまま)

 p = 1, ~2,~\infty のときは, 特別な手法を使わなくても解くことが出来ます.  p = 2 のときは有名なので, ここでは省略します.

p = 1 のとき

 m = \arg\max_{i=1,\ldots,n} |a_i| とします. 複数個ある場合はそのうちの一つを取ってくることにします.  x_m = -\frac{a_0}{a_m}, x_i = 0~(i\ne m) は制約条件を満たし, このとき  | \boldsymbol{x} |_1 = \left|\frac{a_0}{a_m}\right|. ここで制約条件を満たすように  x_m \Delta_m だけ変化させ, 他の  x_i~(i\ne m) も制約条件を満たすように  \Delta_i だけ変化させます. つまり今,

 \displaystyle
\begin{align}
x_m &= -\frac{a_0}{a_m} + \Delta_m, \\
x_i &= \Delta_i~(i\ne m), \\
a_m\Delta_m &= - \sum_{i\ne m}a_i \Delta_i.
\end{align}

3 番目の式を変形させていきます.

 \displaystyle
\begin{align}
a_m\Delta_m &= - \sum_{i\ne m}a_i \Delta_i \\
|a_m| |\Delta_m| &= \left|- \sum_{i\ne m}a_i \Delta_i \right| \\
&\leq \sum_{i\ne m} |a_i| |\Delta_i| \\
&\leq \left(\max_{i\ne m} |a_i| \right) \sum_{i\ne m} |\Delta_i|.
\end{align}

これより, 以下の不等式が成り立ちます.

 \displaystyle
\begin{align}
| \Delta_m | \leq \frac{| a_m |}{\max_{i\ne m} | a_i |}| \Delta_m | \leq \sum_{i\ne m} | \Delta_i |.
\end{align}

今, 超平面までの距離は以下のような不等式で表せます. 最後の右辺は地道な場合分けによって展開できます.

 \displaystyle
\begin{align}
\| \boldsymbol{x} \|_1 = \left| -\frac{a_0}{a_m} + \Delta_m \right| + \sum_{i\ne m}| \Delta_i | \geq \left| -\frac{a_0}{a_m} + \Delta_m \right| + | \Delta_m | \geq \left| \frac{a_0}{a_m} \right|.
\end{align}

よって  p=1 のとき,  m = \arg\max_{i=1,\ldots,n} |a_i| とすると, 超平面上の点  x_m = -\frac{a_0}{a_m}, x_i = 0~(i\ne m) が原点からの最小距離  \left|\frac{a_0}{a_m}\right| を取ります.

p = ∞ のとき

今,  \| \boldsymbol{x} \|_\infty = \max_{i=1,\ldots,n}| x_i | = \epsilon (\geq 0) とすると  \left | \sum^n_{i=1} a_ix_i \right | \leq \sum^n_{i=1} |a_i| \epsilon. この不等式より制約条件  \boldsymbol{a}^\top \boldsymbol{x} + a_0 = 0 を満たすのは,  \epsilon \geq -\frac{a_0}{\sum^n_{i=1} | a_i |} のときとなります. すなわち  \| \boldsymbol{x} \|_\infty = -\frac{a_0}{\sum^n_{i=1} | a_i |} が最小の距離となります. またこのとき等号成立条件を考え,  \boldsymbol{x} = -\frac{a_0}{\sum^n_{i=1} | a_i |}\operatorname{sign} a_i です.

解法 2 (ラグランジュの未定乗数法)

ラグランジュの未定乗数法によって,  1\lt p\leq\infty に対して, 最小  l_p 距離が計算できます.  p=1 のときは  \sum_{i=1}^n |x_i| x_i = 0微分不可能であり, ラグランジュの未定乗数法を使おうとすると面倒臭い場合分けが必要となります. 更に解法 1 から分かる通り, 最適解がその微分不可能な点にあるので, あまりラグランジュの未定乗数法の恩恵を受けられません. よって  1\lt p\leq\infty に対して考えます.

 p>1 のとき,  |x|^p は全ての点で微分可能です. 一応, 原点での挙動を以下のように確認しておきます.

 \displaystyle
\lim_{h\to +0}\frac{|h|^p}{h} = \lim_{h\to -0}\frac{|h|^p}{h} = 0.

ラグランジュの未定乗数法を用いて, 上の最小化問題を解きます. 関数  L(\boldsymbol{x},\lambda) を以下のように定義します.

 \displaystyle
L(\boldsymbol{x},\lambda) = \sum_{i=1}^n | x_i |^p - \lambda (\boldsymbol{a}^\top\boldsymbol{x} + a_0)

これを各変数で微分すると以下のようになります.

 \displaystyle
\begin{align}
\boldsymbol{\nabla}_\boldsymbol{x} L(\boldsymbol{x},\lambda) &= p |\boldsymbol{x}|^{p-1} \text{sign}~\boldsymbol{x}  - \lambda \boldsymbol{a} \\
\nabla_\lambda L(\boldsymbol{x},\lambda) &= -(\boldsymbol{a}^\top\boldsymbol{x} + a_0)
\end{align}

関数  L極値を求めるために  \boldsymbol{\nabla}_\boldsymbol{x} L(\boldsymbol{x},\lambda) = 0, \nabla_\lambda L(\boldsymbol{x},\lambda) = 0 を解きます. これは以下の連立方程式で表されます.

 \displaystyle
\begin{align}
p |\boldsymbol{x}|^{p-1} \text{sign}~\boldsymbol{x}  - \lambda \boldsymbol{a} = 0 \\
\boldsymbol{a}^\top\boldsymbol{x} + a_0 = 0
\end{align}

上の式は両辺に  \operatorname{sign} 関数を掛け合わせることで,  \operatorname{sign}\boldsymbol{x} = \operatorname{sign}\lambda\boldsymbol{a} が得られます. よって

 \displaystyle
\begin{align}
&p |\boldsymbol{x}|^{p-1} \text{sign}~\boldsymbol{x}  - \lambda \boldsymbol{a} = 0\\
\Leftrightarrow &p |\boldsymbol{x}|^{p-1} \operatorname{sign}\lambda\boldsymbol{a}  - \lambda \boldsymbol{a} = 0 \\
\Leftrightarrow &p |\boldsymbol{x}|^{p-1} = |\lambda \boldsymbol{a}| \\
\Leftrightarrow & |\boldsymbol{x}| = \left|\frac{\lambda \boldsymbol{a}}{p}\right|^{\frac{1}{p-1}} \\
\Leftrightarrow & \boldsymbol{x} = \left|\frac{\lambda \boldsymbol{a}}{p}\right|^{\frac{1}{p-1}}\operatorname{sign}\lambda\operatorname{sign}\boldsymbol{a} \\
\end{align}

これを  \boldsymbol{a}^\top\boldsymbol{x} + a_0 = 0 に代入して整理すると以下のようになります.

 \displaystyle
\left| \frac{\lambda}{p} \right|^{\frac{1}{p-1}} \operatorname{sign}\lambda = - \frac{a_0}{\sum_{i=1}^n|a_i|^{\frac{p}{p-1}}}

よって

 \displaystyle
\boldsymbol{x} = - \frac{a_0}{\sum_{i=1}^n|a_i|^{\frac{p}{p-1}}} \cdot \left|\boldsymbol{a}\right|^\frac{1}{p-1}\operatorname{sign}\boldsymbol{a}

のとき, 最小距離となります. またこの  \boldsymbol{x} に対して,  l_p ノルムを計算すると,  \| \boldsymbol{x} \|_p = \frac{|a_0|}{ \| \boldsymbol{a} \|_{\frac{p}{p-1}}} となります.  l_p に関しては解法 1 の結果と合いますが, それを満たす  \boldsymbol{x} は解法1と合いません. これは最初に述べた通り, ラグランジュの未定乗数法では微分可能でない点を考慮していないことが関係していると思われます.

解法 3 (Holder の不等式)

ラボの先輩から聞いた超シンプルかつ  1\leq p\leq \infty と広く成り立つ解法です.

アダマール積を  \odot とします. 制約条件から以下の不等式が導けます.

 \displaystyle
\begin{align}
a_0 &= -\boldsymbol{a}^\top \boldsymbol{x} \\
| a_0 | &= | \boldsymbol{a}^\top \boldsymbol{x} | \leq \sum^n_{i=1} | a_i x_i | \leq \| \boldsymbol{a}^\top \boldsymbol{x} \|_1.
\end{align}

ヘルダーの不等式より,  \frac{1}{p}+\frac{1}{q}=1 とすると

 \displaystyle
\| \boldsymbol{a}^\top \boldsymbol{x} \|_1 \leq \| \boldsymbol{a} \|_q \| \boldsymbol{x} \|_p.

この二つの不等式から

 \displaystyle
\begin{align}
| a_0 | &\leq \| \boldsymbol{a} \|_q \| \boldsymbol{x} \|_p \\
\frac{| a_0 |}{\| \boldsymbol{a} \|_q} &\leq \| \boldsymbol{x} \|_p.
\end{align}

AutoAttack[日本語まとめ]

基本情報

2022年5月時点の adversarial attack SOTA.

論文 [Croce+, ICML20] arxiv.org

github github.com

Abstract (概要)

最近の防御手法は正確な評価が出来ていないため, SOTA が良く分からない. ちゃんとした評価, つまりちゃんとした攻撃が出来ない理由は攻撃や勾配の難読化, マスキングに関するハイパラを上手く調節出来ていないからである. 本論文では, まずPGDを拡張した二つの手法を提案する. これはステップサイズと目的関数の欠陥を改善している. 私達はこれらを二つの補完的な既存の攻撃と組み合わせて, パラメータフリーで高速な攻撃を実現する. 私達はこのアンサンブル手法で50個以上のモデルを攻撃し, 1つの例外を除き, 全てのモデルのロバスト精度を低下させた. そして10%以上の防御手法が機能していないことを明らかにした.

Introduction (導入)

これまで色々な防御手法が提案されてきたが, まともに機能しているのは adversarial training だけである. 理論的保証を持つ手法などもあるが, やはり adversarial training の方が強い. 防御手法が正しく評価できていないのは, パラメータのチューニングを必要としない汎用的な攻撃手法が無いからである. 本論文はこれを提案する.

最も一般的な攻撃手法は PGD だが, これも時には機能しなくなる. これは固定されたステップサイズと cross-entropy (CE) loss が原因である. 私達が提案する Auto-PGD (APGD) はステップサイズを選ぶ必要がなく, また CE loss 以外の損失関数も使う. この手法のパラメータはイテレーション回数だけであり, その他の要素は全て自動的に調節される.

また既存の攻撃が上手くいかない理由の一つとして, 多様性の欠落, つまり FGSM や PGD ばかりを使っていることが問題として考えられる. 攻撃に多様性を生むために私達は white-box FAB と black-box Square Attack を上述の二つの手法に組み合わせる. すなわち4つの攻撃のアンサンブルを行う. 本論文ではこのアンサンブル攻撃を AutoAttack と呼ぶ.

本論文では, 35本以上の論文からなる50種類以上の防御手法を AutoAttack によって評価した. AutoAttack に含まれる3つの white-box な手法は5回のリスタートしか行っていない. 結果としては, 2つの防御手法以外は全て報告された値よりも小さなロバスト精度となった. さらに少しだけ計算量を増やした AutoAttack+ の場合では, 1つを除き, 全て上手くいった. また13個以上のモデルが10%以上のロバスト精度の低下を引き起こしており, これらは防御手法として機能していない.

私達は AutoAttack が究極の攻撃と思っている訳ではないが, ハイパラのチューニング無し, かつ比較的計算量の少ない手法としては良いものだと思っている.

Adversarial examples and PGD (敵対的画像とPGD)

通常の PGD は各イテレーションのステップサイズが固定であり, またランダムスタートを用いる. またノルムに応じて, 勾配は正規化が行われる. 例えば  l_\infty norm であれば, 勾配を符号関数にかける.

Auto-PGD: A budget-aware step size-free variant of PGD (Auto-PGD: step size を選ぶ必要がない PGD の変種)

色々書いているが, 要はステップサイズを徐々に減少させるPGDである. Budget-aware のように budget (予算) という言葉が論文中で使われるが, これはイテレーション回数を指している. Budget-aware という言葉は後述のチェックポイントの計算を指していると思われるが, これもステップサイズを効率的に減少させる枠組みでしかない. Auto-PGD が普通の PGD と異なるのは step-size を減少させるという点と後述の DLR loss だけである.

Gradient step (勾配計算による敵対的画像の更新)

APGD の更新は以下のように普通の PGD にモーメンタムを加えただけである. 下の式の  \alpha は0.75で固定される.

 \displaystyle
  \begin{align}
    z^{(k+1)} &= P_S \left( x^{(k)} + \eta^{(k)} \nabla f(x^{(k)}) \right) \\
    x^{(k+1)} &= P_S \left( x^{(k)} + \alpha \cdot \left( z^{(k+1)} - x^{(k)} \right) + (1-\alpha) \cdot \left( x^{(k)} - x^{(k-1)} \right) \right)
  \end{align}

Step size selection (step size の選択・減少)

始まりの step size  \eta^{(0)} 2\epsilon であり, ここからある条件に応じて, 1/2ずつ減少させていく. 条件を満たしているか判定するチェックポイント  w_j (例えば 0 iteration目, 20 iteration目, 40 iteration目, ...) の設定は後述. 条件は以下の二つのどちらかを満たしていれば, というものである.

  1.  \displaystyle \sum^{w_{j-1}}_{i=w_{j-1}} \boldsymbol{1}_{ f(x^{(i+1)}) \gt f(x^{(i)}) } \lt  \rho \cdot (w_j - w_{j-1})
  2.  \eta^{(w_{j-1})} \equiv \eta^{(w_{j})} and  f^{(w_{j-1})}_{\text{max}} \equiv f^{(w_{j})}_{\text{max}}

ただし,  \boldsymbol{1} は条件を満たしたとき1, そうでなければ0の関数,  f は損失関数,  \rho=0.75,  \equivは両辺の値が一致しているか判定するものである.

条件1の左辺は攻撃が成功した, つまり損失関数の値を上昇させることができたステップの回数である. つまり条件1は, 前回のチェックポイントから今回のチェックポイントまで, 更新が上手くいったステップが全体の75%以下かを判定するものである.

条件2は前回のチェックポイントで step size が更新されず, 一番良い adversarial example も更新されていないときである.

Restarts from the best point (一番良いところからリスタート)

チェックポイントで条件を満たしたら, 次のイテレーションは今までで一番良いやつからスタート.

Exploration vs exploitation (大域的な探索と局所的な最適化)

最適アルゴリズムはグローバルな探索から局所的な最適化に徐々に移ってほしい. 経験的に, 最初の探索には時間をかけてよい. 実際, 最初から小さなステップサイズを選ぶのは, これまでの random start の成功から見ても悪手である. 我々はチェックポイントを  w_j = \lceil p_j N_{\text{iter}} \rceil のように定める. ただし,  p_0 = 0, p_1 = 0.22 であり, 以下のように更新される.

 \displaystyle
    p_{j+1} = p_j + \max \{ p_j - p_{j-1} - 0.03, 0.06 \}

例えば, 100 iteration のとき,  w_0 = 0, w_1 = 22, w_2 = 41, w_3 = 57 である.

Comparison of APGD to usual PGD (通常の PGD と APGD の比較)

APGD と モーメンタム付きの PGD を CE loss とロバスト精度で比較する. つまりステップサイズの調整有り・無しの比較を行う. データセットはMNISTとCIFAR-10である. 通常の PGD のステップサイズは  \epsilon / tで,  t\in\{0.5,1,2,4,10,25,100\}である. APGD のイテレーション回数は  N_{\text{iter}}\in\{25,50,100,200,400,1000\}である.

結果としては, APGD の方が攻撃性能が高いことが分かった. また APGD は大きいイテレーション回数のときは, 序盤で微小な精度の増加を犠牲に, グローバルな探索を行うことで, 最終的により強い攻撃となっている.

An alternative loss (CE loss に対して, もう一つの損失関数)

ある画像の正解クラスを  y , そのクラスのロジットを  z_y, 確率を  p_y とする.

CE loss は  p_y\approx1 のとき,  \nabla_x \text{CE}\approx\boldsymbol{0} となり, 勾配消失する. 勾配消失すると PGD の計算が出来なくなり, 攻撃が上手くいかなくなる.

ここで, 興味深い事例を紹介する. 分類器の最終層の出力, つまりロジットを1000倍するだけで,  p_y\approx 1, すなわち \nabla_x \text{CE}\approx\boldsymbol{0}となる. これは確率を計算する softmax 関数, 更に言えばその内部の exponential 関数の影響である. これは最終層の出力にある大きな値をかけるだけで, CE loss による攻撃は機能しなくなるということを表している.

下のグラフは実際にこれを実験で確認してみたものである. これは上の説明を基に, 最終層の出力を rescaling factor (横軸)で割っている. つまり横にいくほど (大きな数で割るほど), 攻撃が成功しやすくなるということである.

また adversarial attack で良く使われる CW loss は以下のように表され, これはロジットに大きな値をかけても勾配消失しない. だが, これもロジットを大きな値で割ると, 勾配消失が起きる. ちなみに CE loss も超大きな値で割ると勾配消失を起こす (はずである).

 \displaystyle
    \text{CW} = -z_y + \max_{i\ne y}z_i

Difference of Logits Ratio Loss (ロジットの比率の違いを利用した損失関数)

本論文で提案される Difference of Logits Ratio (DLR) loss は以下のようなものである. ただし,  \pi はロジットの降順で決まるクラスである. つまり  z_{\pi_1} は一番大きなロジット.

 \displaystyle
    \text{DLR} = -\frac{z_y-\max_{i\ne y}z_i}{z_{\pi_1}-z_{\pi_3}}

これは各ロジットの値を何倍しても分母と分子で打ち消し合い, 上述のような勾配消失が起きない.

更にこれの targeted attack 用は以下のようになる. 分母で  z_{\pi_3} z_{\pi_4} が出てきているのは  z_{\pi_3} のみを使うと,  z_{\pi_3} = z_t のとき, 定数になってしまうからである.

 \displaystyle
    \text{Targeted-DLR} = -\frac{z_y-z_t}{z_{\pi_1}-(z_{\pi_3}+z_{\pi_4})/2}

APGD versus PGD on different losses (様々な損失関数を用いた通常の PGD と APGD の比較)

PGD と モーメンタム付きの PGD, APGDを比較する. 損失関数としては, CE, CW, DLR を用いた.

結果としては, CE のとき32/43, CW のとき37/43, DLR のとき35/43の割合で APGD が勝った. APGD が負けたモデルは gradient masking / obfuscation が起きていて, 非常に大きい step size が最適となっていた. つまりこれらは不適切な防御モデルである.

APGD はどんな損失関数を用いるときでも, PGDまたはモーメンタム付きのPGDより優れている.

DLR は CE より基本的に優れている. CW は DLR に対して最大で21%悪くなり, また最大でも5%程しか良くならなかったため, 壊滅的な結果を起こさないという意味で DLR の方が優れている.

AutoAttack: an ensemble of parameter-free attacks (チューニングの必要があるパラメータの無いアンサンブル攻撃)

速度の観点で, ランダムスタートの無い \text{APGD}_\text{CE} と9つの target class に攻撃を行う \text{APGD}_\text{CE}^\top , 9つの target class に攻撃を行う \text{FAB}^\top , 1回の実行で5,000クエリを必要とするSquare Attackを比較した. 各 white-box 攻撃 (前半の3つ) では100イテレーションで攻撃を行なった. 結果としては, \text{APGD}_\text{CE} が一番早いという結果となった (当たり前である).

AutoAttack の重要な性質として, アンサンブルの構成要素である4つの攻撃の多様性が挙げられる. APGD は  l_p-ball の中で adversarial example を作るが, FAB は誤分類を達成する最小の摂動を見つけようとする. FAB はロジットの勾配に依るものの, 基本的にgradient masking に強いとされる. Square Attack は score-based なブラックボックス手法であり, ランダムサーチを使うため, 勾配の情報を一切必要としない. Square Attack はクエリ効率と攻撃成功率が高く, 時には white-box 並の強さを誇る. FAB と Square Attack はパラメータ数が少なく, 多くのモデルとデータセットに汎化される. よって私達はこれのパラメータを固定した.

AutoAttackのパラメータは全てのモデルとデータセットで固定される.

Untargeted vs targeted attacks

ここでは  \text{APGD}_{\text{DLR}} と FAB で targeted attack を用いた理由について説明する. なお CE loss は untargeted のとき, randomized defense に対して良い結果を出すので, untargeted のまま使う.

FAB

Untargeted FAB は各 iteration でヤコビアン行列を計算するが, これはクラス数に線形で増加していく. よって巨大データセットでは使えない. これを防ぐために, 私達は targeted ver を使う. これは正解クラスと target class の間の識別境界を線形と考え, 問題を簡単にしたものである.

Experiments (Untargeted と targeted の比較)

ランダムスタートの異なる5種類の untargeted attack と 9 つの target class を持つ targeted attack を考える. 結果としては, CIFAR-10 と CIFAR-100, ImageNet では  \text{APGD}^\top_{DLR} がほとんど全ての場合で良い結果を残した. MNIST だけは Square Attack が一番良い結果となった. これらの結果から  \text{APGD}_{\text{DLR}} と FAB では targeted ver を用いる.

Experiments

Deterministic defenses (決定論的防御手法)

35個の防御手法から50個以上のモデルを用い, 実験を行った. ImageNet では1000枚抽出し, それを評価に用いる.

結果としては, 1つを除き, 全てのモデルで AutoAttack の強さが証明された. また各論文で報告されている値と, 13個以上のモデルで10%以上の乖離が, 8個以上のモデルで30%以上の乖離が見られた. 唯一負けたモデルは180回以上のリスタートと200回のイテレーションを行なっており, 我々より計算的に高価である.

4つの攻撃の中では  \text{APGD}^\top_\text{DLR} が最も良く, また壊滅的な結果となりにくかった. これらの結果は私達が新たに提案した DLR loss が gradient masking に強いことを示している.

Randomized defenses (ランダマイズ的防御手法)

Randomized defense は各施行毎に結果が異なるので, 表の値は平均, かっこの中は標準偏差である. 試行は全部で5回. ランダム性に対抗するために, 今回は untargeted ver で, 各イテレーションでは 20 回の勾配計算の後にその平均を用いている. ここでは FAB を用いなかった. なぜなら FAB は識別境界の上, または非常に近くの adversarial examples を計算するので, ランダム性の影響を受け, adversarial examples じゃ無くなってしまうからだ. と言いつつも表に載ってる様に見えるのだが, 流れ的には載ってる結果でダメと分かったから以後やらなかったという感じらしい. Square Attack は1イテレーションに対し, 20回の試行を行い, そこで平均的にロスが下がったら更新を行った. Square Attack はここで計算量が増えるので, 全体としては1000回のイテレーションを行なった. JEM-0 モデルに攻撃するときは, 5回のリスタートを行い, 各計算では勾配の平均を使用しない. これはランダマイズの影響が少ないからである. また JEM-0 モデルに対する adversarial example を JEM-1, 10 に使い回した.

結果としては, AutoAttack は常に良い結果を出し, また  \text{APGD}^\top_\text{CE} が最も良くなった.

Analysis of SOTA of adversarial defenses

最も頑健な手法達は adversarial training やその派生系だった. これらの中で一歩抜きん出ているものは追加のデータを用いる手法だった. また SOTA を主張しているいくつかの手法は全く頑健ではなかった. 興味深いことに MNIST で最も頑健だったモデルはその論文内で理論的に示された下限値93.32%と類似した結果となった (93.96%).

Appendix

結果だけ箇条書きで抽出

  • APGD と普通の PGD, つまりモーメンタムを使用していない PGD を比べても APGD の方が良かった.
  • 多くのデータセットとモデルに対して, APGD と 通常の PGD, モーメンタム付き PGD の比較を行ったが, APGD の方が良かった.
  •  l_\infty の実験では各 step で, 勾配に符号関数をかけた.  l_2 では, 正規化した. FAB のハイパラは Advertorch のを用いた. Square Attack は正方形のサイズ  p を0.8とした. これは元コードに同じである. また  p に関して piecewise constant scheduler を使用し, これは何のリスケーリングも行わなければ 10000 クエリの制限があることを示唆している. ただし, 我々は最大でも 5000 クエリしか行っていない (この辺の文章意味分かってないです. すみません.).
  • 大きいモデルだからといって, 性能が良いとは限らない.
  • 通常の PGD は  \epsilon / 4 が平均的に良いが, それでも分散は大きい.
  • 普通では上手くいかない step size  2\epsilon のような攻撃が上手くいっているときは, ランダムサーチが当たったようなものである. このようなモデルは gradient masking されている.
  • CE loss は元のクラスの確率を下げるという特性から, 誤分類さえ起こせば良いという訳ではない randomized defense に良い結果を出す.

Hierarchical Adversarial Robustness

Improving Hierarchical Adversarial Robustness of Deep Neural Networks [Ma+, arXiv20]

Huawei Intern で書かれた論文.

2021/2/17 [arXiv]

簡単のため, 以下のような略語を使用する.

  • AE: Adversarial Examples
  • AA: Adversarial Attack
  • clean: AAを受けていない自然画像
  • AT: Adversarial Training
  • AR: Adversarial Robustness
  • BN: Batch Normalization

概要

自動運転システムが歩行者を車と誤認した場合, 車をバスと誤認した場合よりも遥かに危険. 粗いクラスで騙すような hierarchical adversarial examples とその生成手法, Hierarchical Adversarially Robust (HAR) という防御手法の提案.

経験則

untargeted attackは粗いラベル内での移動が見られる. 下の表は (粗いラベルで AA 失敗) / (細かいラベルで AA 成功).

f:id:kamakuraviel:20220102201755p:plain

Worst-case targeted PGD attack

元のラベルが含まれていないような粗いラベルの集合に対して, target attack (PGD) を行う.

f:id:kamakuraviel:20220102201913p:plain

HAR Network

粗い分類を行う分類器  G(x) = [g_1,\ldots,g_c] と細かい分類を行う分類器  H_1,\ldots,H_c,  H_i(x)=[h_1^i,\ldots,h_j^i] によって構成される.  G(x) H(x) は別々に訓練される. 最終的な予測は  [g_1H_1(x),\ldots,g_cH_c(x)].

f:id:kamakuraviel:20220102202042p:plain

実験設定

データセット

f:id:kamakuraviel:20220102184936p:plain

モデル

パラメータ数で差がつかないようにあえて HAR の各ネットワークの表現力を落としている.

  • CIFAR100, CIFAR-100-5x5
    • バニラモデルは ResNet50
    • HAR の各ネットワークは ResNet10
  • CIFAR10
    • バニラモデルは ResNet34
    • HAR の各ネットワークは ResNet10

訓練設定

  • 200 epoch. 学習率は0.1, 100, 150 epoch で x 0.1.
  • batch size 128
  • SGD, momentum 0.9, weight decay 2e-4.

普通のネットワークの訓練設定

  • 普通
  • ADV: 10-untargeted-PGD の AT
  • ADV-T: 10-random-targeted-PGD の AT. 粗いクラスが違うところからランダムに選ばれる.
  • TRADES. 正則化項に関して探索を行い, AR が最も良かったものを使う. それ以外の設定は ADV-hCEと同じ.
  • ADV-hCE: hCE の 10-untargeted-PGD. Hierarchical CE =  \ell(F(x), y) + \ell(G(x), z).  G(x) F(x) の合計値.

attack

  • 基本は l-inf, supple に l2
  • PGD の step size は  \epsilon / 4
  • worst-case targeted attack では test set から 1000 個ランダムに選択した.

実験

普通の PGD

  • 普通のPGDでは細かいクラスでの移動が見られる.
  • ADV-T を用いて学習した通常のモデルは ADV と比較して, 階層的頑健性が向上している.
  • ADV-hCE は階層的頑健性において標準的な ADV を上回らない (のでここに結果として載せていない).

f:id:kamakuraviel:20220102203046p:plain

worst-case targeted attack

  • 普通の PGD では影響のないクラスへの移動しか行われないが, worst-case targeted attack は粗いクラスの正解率を下げる.
  • ADV-T による階層的頑健性の向上はより強力な階層的攻撃に対しては有効でない
  • 8/255以上では ADV 訓練されたモデルは ADV-T より優れている.
  • ADV した HAR は階層的頑健性を大幅に向上させる.
  • TRADES では PGD200 で通常のモデルと比較して0.1%の精度向上.

f:id:kamakuraviel:20220102204222p:plain

corse network への攻撃

  • 下の表は HAR の corse network に対して target PGD 8/255 をしたもの. 比較のために, untargeted attack と HAR 全体の結果も載せている.
  • corse network を使用して生成された摂動は HAR 全体を使用して生成されたものと比較して弱い攻撃である

f:id:kamakuraviel:20220102215549p:plain

Appendix

TRADES の詳しい設定

CIFAR10, ResNet10に対する結果. 今回の実験では他の全てのデータセットに対して  \beta=9 を使用した.

f:id:kamakuraviel:20220107220114p:plain

L2 の結果

f:id:kamakuraviel:20220107231506p:plain

f:id:kamakuraviel:20220107231602p:plain

CIFAR10, CIFAR100-5x5 の結果

f:id:kamakuraviel:20220107231845p:plain

ADV-hCE の結果

ADV-hCEで使用する PGD は hCE に基づいて生成されるので, これを用いて学習したモデルは hCE で生成された untargeted-PGDに対して HAR が向上する. しかしこのような HAR の向上はより強力な worst-case targeted attack に対しては維持されない.

f:id:kamakuraviel:20220107232655p:plain

ICLR21での評価

  • 重要な問題設定だが, 実験の方法論にいくつか疑問がある.
  • 標準的な状況設定で階層的な分類を扱うためのアプローチ (学習損失とアーキテクチャの両方) は多数存在しているので, それらを AR に適応させる術も考えられるべきである.
  • 適切なベースラインや徹底したロバスト性評価を提供していない.

なおこれらの指摘を受けて, その後この論文は改訂されている.

【Python】多重継承とABC

関数が被っている場合, 先頭のクラスの関数しか呼ばれない

class A:
    def __init__(self):
        print('a')
        
class B:
    def __init__(self):
        print('b')
        
class C(A, B):
    pass
        
C() #=> a

先頭のクラスの親クラスで定義されている関数と二番目のクラスで定義されている関数では後者が採用される

class A:
    def func(self):
        print('a')
        
class B(A):
    pass

class C:
    def func(self):
        print('c')
        
class D(B, C):
    pass
        
D().func() #=> c

ABCを継承していてもインスタンスを生成することはできる

from abc import ABC

class A(ABC):
    def __init__(self):
        print('a')
        
A() #=> a

他のクラスで同名の関数を定義していてもそのクラスがABCクラスを継承していなければErrorが発生する

from abc import ABC, abstractmethod

class A(ABC):
    @abstractmethod
    def f(self):
        pass
    
class B(A):
    pass

class C:
    def f(self):
        print('c')
        
class D(B, C):
    pass

D() #=> TypeError: Can't instantiate abstract class D with abstract methods f