みらいテックラボ

音声・画像認識や機械学習など, 週末プログラマである管理人が興味のある技術の紹介や実際にトライしてみた様子などメモしていく.

AutoKerasを試してみる(1)

(株)クラスキャットの記事「AutoKeras 1.0 : Tutorials : 画像分類」[1]で, AutoML(Automated Machine Learning)のOSS実装であるAutoKeras[2]がバージョン1.0になったことを知った.

AutoMLは機械学習プロセスの自動化を目的とした技術で, GoogleのCloud AutoMLがよく知られている.
ちなみに, Cloud AutoML Visionは, CODE for YAMATOKORIYAMAで開発を進めている「Kingyo AI Navi」[3]の金魚の品種識別でも使用しているサービスだ.


以前からAutoKerasが開発されていることは知っていたが, 今回バージョンが1.0になったので画像分類を少し試してみることにした.


1. 学習
画像分類を試す場合, よく手書き数字の画像データセット「MNIST」を使用する場合が多いのだが, CNNなどを使用するとaccuracyが0.99以上になるなどモデルの差が分かりにくい.
そこで, 今回は衣料品画像の画像データセット「Fashion-MNIST」[4]を使用して試してみる.

f:id:moonlight-aska:20200329011435p:plain


[コード]

from PIL import Image

# autokeras, tensorflow
import autokeras as ak
from tensorflow.keras.datasets import fashion_mnist

(train_images, train_labels), (test_images, test_labels) = fashion_mnist.load_data()

x_train = train_images / 255.0
x_test = test_images / 255.0
y_train = train_labels
y_test = test_labels

# インスタンス生成
clf = ak.ImageClassifier(num_classes=10,
                         loss='categorical_crossentropy',
                         metrics='accuracy',
                         max_trials=5,
                         directory='./outputs/',
                         objective='val_accuracy',
                         seed=7)

# 学習(ベストなモデル, ハイパーパラメータの探索)
clf.fit(x_train, y_train, epochs=10)

# 予測
predicted_y = clf.predict(x_test)
# 評価
print(clf.evaluate(x_test, y_test))
# モデルのExport
model = clf.export_model()
model.save('./model/fmnist_trial5+epoch10.h5')

さすが, モデル構造やハイパーパラメータなどを自動的に決定するだけあって, コードも非常に簡単だ.

Linux PC(CPU:Core i7 7700, RAM:16GB, GPU:GTX-1060, OS:Ubuntu18.04)で実行すること約20分で一応学習終了...


2. 識別
先の学習済モデルを用いて識別を行う.

[コード]

from PIL import Image

# autokeras, tensorflow
import autokeras as ak
from tensorflow.keras.models import load_model
from tensorflow.keras.utils import to_categorical
from tensorflow.keras.datasets import fashion_mnist

(train_images, train_labels), (test_images, test_labels) = fashion_mnist.load_data()

test_images = test_images.reshape(test_images.shape + (1,))

x_test = test_images / 255.0
y_test = to_categorical(test_labels)

# モデルの読み込み
model = load_model('./model/fmnist_trial5+epoch10.h5', custom_objects=ak.CUSTOM_OBJECTS)
# 評価
result = model.evaluate(x_test, y_test)
print(result)

[実行結果]

(tensorflow2) aska@moonlight:~/work/Fashion-MNIST$ python evaluate_autokeras.py 2020-03-29 00:14:23.270877: I tensorflow/stream_executor/platform/default/dso_loader.cc:44] Successfully opened dynamic library libnvinfer.so.6
    :
10000/10000 [==============================] - 1s 125us/sample - loss: 0.2337 - accuracy: 0.9196
[0.23365052340626716, 0.9196]

accuracyは0.920で, もっと高い精度がでるかと思っていたが, それほどではなかった.

ちなみに, Keras DocumentationのMnist cnn[5]のサンプルコードでFashion-MNISTを試すと, 0.925であった.

(tensorflow2) aska@moonlight:~/work/Fashion-MNIST$ python mnist_cnn.py 
Using TensorFlow backend.
2020-03-28 23:39:10.844111: I tensorflow/stream_executor/platform/default/dso_loader.cc:44] Successfully opened dynamic library libnvinfer.so.6
    :
60000/60000 [==============================] - 5s 83us/step - loss: 0.1718 - accuracy: 0.9380 - val_loss: 0.2127 - val_accuracy: 0.9254
Test loss: 0.21271519023776053
Test accuracy: 0.9254000186920166


3. AutoKerasを使う上での注意点
3.1 tf.kerasを使用
 kerasのAPIを使用する場合には, tf.kerasを使用する.

[不具合例]
・keras.models.load_modelを利用すると, 以下のようなエラーが発生する.

(tensorflow2) aska@moonlight:~/work/Fashion-MNIST$ python evaluate_autokeras.py 2020-03-29 00:26:45.084879: I tensorflow/stream_executor/platform/default/dso_loader.cc:44] Successfully opened dynamic library libnvinfer.so.6
2020-03-29 00:26:45.085942: I tensorflow/stream_executor/platform/default/dso_loader.cc:44] Successfully opened dynamic library libnvinfer_plugin.so.6
Using TensorFlow backend.
Traceback (most recent call last):
  File "evaluate_autokeras.py", line 17, in <module>
    model = load_model('./model/fmnist_trial5+epoch10.h5', custom_objects=ak.CUSTOM_OBJECTS)
  File "/home/aska/anaconda3/envs/tensorflow2/lib/python3.7/site-packages/keras/engine/saving.py", line 492, in load_wrapper
    return load_function(*args, **kwargs)
  File "/home/aska/anaconda3/envs/tensorflow2/lib/python3.7/site-packages/keras/engine/saving.py", line 584, in load_model
    model = _deserialize_model(h5dict, custom_objects, compile)
  File "/home/aska/anaconda3/envs/tensorflow2/lib/python3.7/site-packages/keras/engine/saving.py", line 274, in _deserialize_model
    model = model_from_config(model_config, custom_objects=custom_objects)
  File "/home/aska/anaconda3/envs/tensorflow2/lib/python3.7/site-packages/keras/engine/saving.py", line 627, in model_from_config
    return deserialize(config, custom_objects=custom_objects)
  File "/home/aska/anaconda3/envs/tensorflow2/lib/python3.7/site-packages/keras/layers/__init__.py", line 168, in deserialize
    printable_module_name='layer')
  File "/home/aska/anaconda3/envs/tensorflow2/lib/python3.7/site-packages/keras/utils/generic_utils.py", line 147, in deserialize_keras_object
    list(custom_objects.items())))
  File "/home/aska/anaconda3/envs/tensorflow2/lib/python3.7/site-packages/keras/engine/network.py", line 1056, in from_config
    process_layer(layer_data)
  File "/home/aska/anaconda3/envs/tensorflow2/lib/python3.7/site-packages/keras/engine/network.py", line 1042, in process_layer
    custom_objects=custom_objects)
  File "/home/aska/anaconda3/envs/tensorflow2/lib/python3.7/site-packages/keras/layers/__init__.py", line 168, in deserialize
    printable_module_name='layer')
  File "/home/aska/anaconda3/envs/tensorflow2/lib/python3.7/site-packages/keras/utils/generic_utils.py", line 149, in deserialize_keras_object
    return cls.from_config(config['config'])
  File "/home/aska/anaconda3/envs/tensorflow2/lib/python3.7/site-packages/keras/engine/base_layer.py", line 1179, in from_config
    return cls(**config)
  File "/home/aska/anaconda3/envs/tensorflow2/lib/python3.7/site-packages/keras/legacy/interfaces.py", line 91, in wrapper
    return func(*args, **kwargs)
TypeError: __init__() got an unexpected keyword argument 'ragged'


3.2 autokeras.CUSTOM_OBJECTSの修正
load_modelを使用して学習済モデルを読み込む場合, CUSTOM_OBJECTSの修正が必要.
2020/3/29時点では, issue #1031[6]が反映されてないため, 以下のようなエラーが発生する.

(tensorflow2) aska@moonlight:~/work/Fashion-MNIST$ python evaluate_autokeras.py 
2020-03-29 00:38:48.560065: I tensorflow/stream_executor/platform/default/dso_loader.cc:44] Successfully opened dynamic library libnvinfer.so.6
2020-03-29 00:38:48.561123: I tensorflow/stream_executor/platform/default/dso_loader.cc:44] Successfully opened dynamic library libnvinfer_plugin.so.6
Traceback (most recent call last):
  File "evaluate_autokeras.py", line 17, in <module>
    model = load_model('./model/fmnist_trial5+epoch10.h5', custom_objects=ak.CUSTOM_OBJECTS)
  File "/home/aska/anaconda3/envs/tensorflow2/lib/python3.7/site-packages/tensorflow_core/python/keras/saving/save.py", line 146, in load_model
    return hdf5_format.load_model_from_hdf5(filepath, custom_objects, compile)
  File "/home/aska/anaconda3/envs/tensorflow2/lib/python3.7/site-packages/tensorflow_core/python/keras/saving/hdf5_format.py", line 168, in load_model_from_hdf5
    custom_objects=custom_objects)
  File "/home/aska/anaconda3/envs/tensorflow2/lib/python3.7/site-packages/tensorflow_core/python/keras/saving/model_config.py", line 55, in model_from_config
    return deserialize(config, custom_objects=custom_objects)
  File "/home/aska/anaconda3/envs/tensorflow2/lib/python3.7/site-packages/tensorflow_core/python/keras/layers/serialization.py", line 106, in deserialize
    printable_module_name='layer')
  File "/home/aska/anaconda3/envs/tensorflow2/lib/python3.7/site-packages/tensorflow_core/python/keras/utils/generic_utils.py", line 303, in deserialize_keras_object
    list(custom_objects.items())))
  File "/home/aska/anaconda3/envs/tensorflow2/lib/python3.7/site-packages/tensorflow_core/python/keras/engine/network.py", line 937, in from_config
    config, custom_objects)
  File "/home/aska/anaconda3/envs/tensorflow2/lib/python3.7/site-packages/tensorflow_core/python/keras/engine/network.py", line 1893, in reconstruct_from_config
    process_layer(layer_data)
  File "/home/aska/anaconda3/envs/tensorflow2/lib/python3.7/site-packages/tensorflow_core/python/keras/engine/network.py", line 1875, in process_layer
    layer = deserialize_layer(layer_data, custom_objects=custom_objects)
  File "/home/aska/anaconda3/envs/tensorflow2/lib/python3.7/site-packages/tensorflow_core/python/keras/layers/serialization.py", line 106, in deserialize
    printable_module_name='layer')
  File "/home/aska/anaconda3/envs/tensorflow2/lib/python3.7/site-packages/tensorflow_core/python/keras/utils/generic_utils.py", line 292, in deserialize_keras_object
    config, module_objects, custom_objects, printable_module_name)
  File "/home/aska/anaconda3/envs/tensorflow2/lib/python3.7/site-packages/tensorflow_core/python/keras/utils/generic_utils.py", line 250, in class_and_config_for_serialized_keras_object
    raise ValueError('Unknown ' + printable_module_name + ': ' + class_name)
ValueError: Unknown layer: Normalization

[修正方法]
{autokerasのインストール先}/autokeras/keras_layers.py内のCUSTOM_OBJECTSを以下のように修正する.

CUSTOM_OBJECTS = {
  'CategoricalEncoding': CategoricalEncoding,
  'Sigmoid': Sigmoid,
  'Normalization':preprocessing.Normalization
}

今回, AutoKerasを少し試してみて一応動作は確認できたが, Accuracyだけをみると比較したMnist cnnの方が性能がよかったので, まだAutoKerasのすごさは実感できていない.
AutoKerasでモデル構造やハイパーパラメータを自動決定してくれ, 識別精度もよくなってくるといろいろと使い道がありそうなので, 引き続き調査していく予定!!

----
[1] AutoKeras 1.0 : Tutorials : 画像分類 - TensorFlow 2.x
[2] AutoKeras
[3] 「Kingyo AI Navi」のアプリ化を考える(1)~(6)
[4] zalandoresearch/fashion-mnist: A MNIST-like fashion product database. Benchmark
[5] Mnist cnn - Keras Documentation
[6] fix bug 'ValueError: Unknown layer: Normalization' #1031