犬種ドラフト

```python
%cd/content/drive/My Drive/dog_folder

from PIL import Image
import os, glob
import numpy as np
from PIL import ImageFile
# IOError: image file is truncated (0 bytes not processed)回避のため
ImageFile.LOAD_TRUNCATED_IMAGES = True

classes = ["ラブラドールレトリバー", "ミニチュアダックスフンド","ゴールデンレトリバー","ダルメシアン",
"コーギー",  "ポメラニアン" ]
num_classes = len(classes)
image_size = 64
num_testdata = 25

X_train = []
X_test  = []
y_train = []
y_test  = []

for index, classlabel in enumerate(classes):
    photos_dir = "./" + classlabel
    files = glob.glob(photos_dir + "/*.jpg")
    for i, file in enumerate(files):
        image = Image.open(file)
        image = image.convert("RGB")
        image = image.resize((image_size, image_size))
        data = np.asarray(image)
        if i < num_testdata:
            X_test.append(data)
            y_test.append(index)
        else:

            # angleに代入される値
            # -20
            # -15
            # -10
            #  -5
            # 0
            # 5
            # 10
            # 15
            # 画像を5度ずつ回転
            for angle in range(-20, 20, 5):

                img_r = image.rotate(angle)
                data = np.asarray(img_r)
                X_train.append(data)
                y_train.append(index)
                # FLIP_LEFT_RIGHT　は 左右反転
                img_trains = img_r.transpose(Image.FLIP_LEFT_RIGHT)
                data = np.asarray(img_trains)
                X_train.append(data)
                y_train.append(index)

X_train = np.array(X_train)
X_test  = np.array(X_test)
y_train = np.array(y_train)
y_test  = np.array(y_test)

xy = (X_train, X_test, y_train, y_test)
np.save("./typesofdogs.npy", xy)
```

```python
from keras.models import Sequential
from keras.layers import Conv2D, MaxPooling2D
from keras.layers import Activation, Dropout, Flatten, Dense
from tensorflow.keras.optimizers import RMSprop
from keras.utils import np_utils
import keras
import numpy as np

classes = ["ラブラドールレトリバー", "ミニチュアダックスフンド","プードル","ブルドッグ","ゴールデンレトリバー","秋田犬 ","ダルメシアン",
"コーギー", "シェトランドシープドッグ" ,"チワワ" ,"シベリアンハスキー" ,
"シェパード", "ポメラニアン" ,"セントバーナード"  ]
num_classes = len(classes)
image_size = 64

# データを読み込む関数

def load_data():
    X_train, X_test, y_train, y_test = np.load("typesofdogs.npy", allow_pickle=True)
    # 入力データの各画素値を0-1の範囲で正規化(学習コストを下げるため)
    X_train = X_train.astype("float") / 255
    X_test  = X_test.astype("float") / 255
    # to_categorical()にてラベルをone hot vector化
    y_train = np_utils.to_categorical(y_train, num_classes)
    y_test  = np_utils.to_categorical(y_test, num_classes)

    return X_train, y_train, X_test, y_test

# モデルを学習する関数

def train(X, y, X_test, y_test):
    model = Sequential()

    # Xは(1200, 64, 64, 3)
    # X.shape[1:]とすることで、(64, 64, 3)となり、入力にすることが可能です。
    model.add(Conv2D(32,(3,3), padding='same',input_shape=X.shape[1:]))
    model.add(Activation('relu'))
    model.add(Conv2D(32,(3,3)))
    model.add(Activation('relu'))
    model.add(MaxPooling2D(pool_size=(2,2)))
    model.add(Dropout(0.1))

    model.add(Conv2D(64,(3,3), padding='same'))
    model.add(Activation('relu'))
    model.add(Conv2D(64,(3,3)))
    model.add(Activation('relu'))
    model.add(MaxPooling2D(pool_size=(2,2)))
    model.add(Dropout(0.25))

    model.add(Flatten())
    model.add(Dense(512))
    model.add(Activation('relu'))
    model.add(Dropout(0.45))
    model.add(Dense(14))
    model.add(Activation('softmax'))

    # https://keras.io/ja/optimizers/
    # 今回は、最適化アルゴリズムにRMSpropを利用
    opt = RMSprop(lr=0.00005, decay=1e-6)
    # https://keras.io/ja/models/sequential/
    model.compile(loss='categorical_crossentropy',optimizer=opt,metrics=['accuracy'])
    model.fit(X, y, batch_size=28, epochs=40)
    # HDF5ファイルにKerasのモデルを保存
    model.save('./cnn.h5')

    return model


# メイン関数データの読み込みとモデルの学習を行います。

def main():
    # データの読み込み
    X_train, y_train, X_test, y_test = load_data()

    # モデルの学習
    model = train(X_train, y_train, X_test, y_test)

main()




```


![ワンコ.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2192130/5c69ab10-cdb5-19ab-4973-e737ae376647.png)


今回は、ダウンロードしたラブラドールレトリバーの画像をLabradorRetriever.jpgというファイル名でアップロードし、変数testpic に代入します。
画像はこちらからダウンロード可能です。


```python

from PIL import Image
import keras
import sys, os
import numpy as np
from keras.models import load_model

imsize = (64, 64)

"""
LabradorRetriever.jpgというファイル名の画像をGoogle Colab上にアップロードする方法は2通りあります。
1つが、下記のコードを実行し画像をアップロードする方法
from google.colab import files
uploaded = files.upload()
2つ目が、Colab左メニューの>アイコンを押して、目次、コード スニペット、ファイル
の3つ表示されるますが、右のファイルタブから画像をアップロードする方法です。
このファイルタブをクリックするとアップロードと更新の2つがありますが、
アップロードを押すと画像をアップロードすることが可能です。
"""

testpic     = "./ミニチュアダックスフンド.jpeg"
keras_param = "./cnn.h5"

def load_image(path):
    img = Image.open(path)
    img = img.convert('RGB')
    # 学習時に、(64, 64, 3)で学習したので、画像の縦・横は今回 変数imsizeの(64, 64)にリサイズします。
    img = img.resize(imsize)
    # 画像データをnumpy配列の形式に変更
    img = np.asarray(img)
    img = img / 255.0
    return img

model = load_model(keras_param)
img = load_image(testpic)
prd = model.predict(np.array([img]))[0]
print(prd) # 精度の表示
prelabel = np.argmax(prd)

classes = ["ラブラドールレトリバー","ミニチュアダックスフンド","プードル","ブルドッグ","ゴールデンレトリバー","秋田犬 ","ダルメシアン",
"コーギー", "シェトランドシープドッグ" ,"チワワ" ,"シベリアンハスキー" ,
"シェパード", "ポメラニアン" ,"セントバーナード" ]
pred_answer = "これは " + classes[prelabel] + "です"
print(pred_answer)
```

先ほどのラブラドールレトリバーの画像を予測させて見ると、次のように正しく認識できています。

スクリーンショット



```python
for i in range(16):
 
   print("{}の確率: {}%".format(classes[i],int(prd[i]*100)))
```

※万が一上記の推論のプログラムで、cnn.h5が存在しないというようなエラーが出た場合、うまく学習フェースのセクションのプログラムが動いていないかと思います。
その場合は、こちらからcnn.h5をダウンロードしご利用ください。

```python
>>> ラブラドールレトリバー
```

念のためにミニチュアダックスフンドの画像でも検証を行います。

ラブラドールレトリバーの画像と同様の方法で以下の猫の画像「Dachshund.jpg」をアップロードし、変数testpicを「./LabradorRetriever.jpg」から「./Dachshund.jpg」に変更し、先ほどのコードを再度実行します 。

#### ミニチュアダックスフンドの画像は、インターネットからお好きなものをダウンロードしてアップロードしてください。 

```python
>>> ミニチュアダックスフンド
```

#### もし、より精度を上げたい場合には画像収集時の引数max_numを増やすことで学習に使うデータ数を増やして再学習させてみましょう。

モデルの方は完成しましたので、その後作成していた下記の「Flask」「HTML」「CSS」のコードを作成。