5. 파이썬

[텐서플로2] 개와 고양이 구분하기

패스트코드블로그 2020. 5. 14. 22:38
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
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
"""
Instructions for updating:
Use tf.where in 2.0, which has the same broadcast rule as np.where
Traceback (most recent call last):
  File "C:/Users/ezen/PycharmProjects/tensorflow191005/advanced/cats_and_dogs.py", line 174, in <module>
    m.execute()
  File "C:/Users/ezen/PycharmProjects/tensorflow191005/advanced/cats_and_dogs.py", line 47, in execute
    history = self.train_model()
  File "C:/Users/ezen/PycharmProjects/tensorflow191005/advanced/cats_and_dogs.py", line 136, in train_model
    steps_per_epoch=self.total_train // self.batch_size,
TypeError: unsupported operand type(s) for //: 'NoneType' and 'int'
"""
 
import tensorflow as tf
 
from tensorflow.keras.models import Sequential
from tensorflow.keras.layers import Dense, Conv2D, Flatten, Dropout, MaxPooling2D
from tensorflow.keras.preprocessing.image import ImageDataGenerator
import os
import numpy as np
import matplotlib.pyplot as plt
from tensorflow.python.keras import datasets
from tensorflow import keras
 
class CnnModel:
    def __init__(self):
        self.batch_size = 128
        self.epochs = 1 # 시간절약
        self.IMG_HEIGHT = 150
        self.IMG_WIDTH = 150
        self.train_dir = None
        self.validation_dir = None
        self.train_cats_dir = None
        self.train_dogs_dir = None
        self.validation_cats_dir = None
        self.validation_dogs_dir = None
        self.train_data_gen = None
        self.total_train = None
        self.total_val = None
        self.val_data_gen = None
 
    def execute(self):
        while 1:
            def print_menu():
                print('0. EXIT\n'
                      '1. SAVE\n'
                      '2. LOAD\n')
                return input('CHOOSE ONE\n')
            menu = print_menu()
            print('MENU %s' % menu)
            if menu == '0':
                break
            elif menu == '1':
                self.download_data()
                # sample_training_images = self.preparation_data()
                # self.plotImages(sample_training_images[:5])
                self.create_model()
 
            elif menu == '2':
                history = self.train_model()
                self.visualize_training_results(history)
 
    def download_data(self):
        (train_images, train_labels), (test_images, test_labels) = datasets.mnist.load_data()
        train_images = train_images.reshape((6000028281))
        test_images = test_images.reshape((1000028281))
        # 픽셀 값을 0~1 사이로 정규화합니다.
        train_images, test_images = train_images / 255.0, test_images / 255.0
        _URL = 'https://storage.googleapis.com/mledu-datasets/cats_and_dogs_filtered.zip'
        path_to_zip = tf.keras.utils.get_file('cats_and_dogs.zip', origin=_URL, extract=True)
        PATH = os.path.join(os.path.dirname(path_to_zip), 'cats_and_dogs_filtered')
        self.train_dir = os.path.join(PATH, 'train')
        self.validation_dir = os.path.join(PATH, 'validation')
        self.train_cats_dir = os.path.join(self.train_dir, 'cats')  # directory with our training cat pictures
        self.train_dogs_dir = os.path.join(self.train_dir, 'dogs')  # directory with our training dog pictures
        self.validation_cats_dir = os.path.join(self.validation_dir, 'cats')  # directory with our validation cat pictures
        self.validation_dogs_dir = os.path.join(self.validation_dir, 'dogs')  # directory with our validation dog pictures
        num_cats_tr = len(os.listdir(self.train_cats_dir))
        num_dogs_tr = len(os.listdir(self.train_dogs_dir))
        num_cats_val = len(os.listdir(self.validation_cats_dir))
        num_dogs_val = len(os.listdir(self.validation_dogs_dir))
        self.total_train = num_cats_tr + num_dogs_tr
        self.total_val = num_cats_val + num_dogs_val
        print('total training cat images:', num_cats_tr)
        print('total training dog images:', num_dogs_tr)
        print('total validation cat images:', num_cats_val)
        print('total validation dog images:', num_dogs_val)
        print("--")
        print("Total training images:", self.total_train)
        print("Total validation images:", self.total_val)
 
    def preparation_data(self)->object:
        train_image_generator \
            = ImageDataGenerator(rescale=1. / 255)  # Generator for our training data
        validation_image_generator \
            = ImageDataGenerator(rescale=1. / 255)  # Generator for our validation data
        self.train_data_gen \
            = train_image_generator\
            .flow_from_directory(batch_size=self.batch_size,
                                 directory=self.train_dir,
                                 shuffle=True,
                                 target_size=(self.IMG_HEIGHT, self.IMG_WIDTH),
                                 class_mode='binary')
        self.val_data_gen \
            = validation_image_generator\
            .flow_from_directory(batch_size=self.batch_size,
                                 directory=self.validation_dir,
                                 target_size=(self.IMG_HEIGHT, self.IMG_WIDTH),
                                 class_mode='binary')
        sample_training_images, _ = next(self.train_data_gen)
        return sample_training_images
 
    def plotImages(self,images_arr):
        fig, axes = plt.subplots(15, figsize=(2020))
        axes = axes.flatten()
        for img, ax in zip(images_arr, axes):
            ax.imshow(img)
            ax.axis('off')
        plt.tight_layout()
        plt.show()
 
    def create_model(self):
        model = Sequential([
            Conv2D(163, padding='same',
                   activation='relu',
                   input_shape=(self.IMG_HEIGHT, self.IMG_WIDTH, 3)),
            MaxPooling2D(),
            Conv2D(323, padding='same', activation='relu'),
            MaxPooling2D(),
            Conv2D(643, padding='same', activation='relu'),
            MaxPooling2D(),
            Flatten(),
            Dense(512, activation='relu'),
            Dense(1, activation='sigmoid')
        ])
        model.compile(optimizer='adam',
                      loss='binary_crossentropy',
                      metrics=['accuracy'])
        print('---------- MODEL SUMMARY -------------')
        print(model.summary())
        model.save('cats_and_dogs.h5')
        print('======= 모델 훈련 종료 ======')
 
    def train_model(self):
        print('케라스에서 모델 호출')
        model = keras.models.load_model('cats_and_dogs.h5')
        history = model.fit_generator(
            self.train_data_gen,
            steps_per_epoch=self.total_train // self.batch_size,
            epochs=1# 시간절약
            validation_data=self.val_data_gen,
            validation_steps=self.total_val // self.batch_size
        )
        return history
 
    @staticmethod
    def visualize_training_results(history):
        acc = history.history['accuracy']
        val_acc = history.history['val_accuracy']
 
        loss = history.history['loss']
        val_loss = history.history['val_loss']
 
        epochs_range = range(1# epochs 1은 시간절약
 
        plt.figure(figsize=(88))
        plt.subplot(121)
        plt.plot(epochs_range, acc, label='Training Accuracy')
        plt.plot(epochs_range, val_acc, label='Validation Accuracy')
        plt.legend(loc='lower right')
        plt.title('Training and Validation Accuracy')
 
        plt.subplot(122)
        plt.plot(epochs_range, loss, label='Training Loss')
        plt.plot(epochs_range, val_loss, label='Validation Loss')
        plt.legend(loc='upper right')
        plt.title('Training and Validation Loss')
        plt.show()
 
 
 
 
 
if __name__ == '__main__':
 
    m = CnnModel()
    m.execute()
 
 
 
cs