다운받은 pretrained model 관련 파일들 중에서 예측에 필요한 파일은 frozen_inference_graph.pb 이다.
그니까 우리의 목표는 아래와 같은 결과 사진을 얻는 것이고,
이를 위해선 하드디스크에 저장돼 있는 frozen_inference_graph.pb 파일을 메모리에 올려 실행해줘야한다는 말이다.
그래서 이번 글에선 frozen_inference_graph.pb를 메모리에 올리는 과정까지 알아보겠다.
글 시작에 앞서 protocol buffer와 관련된 글,
[인공지능 용어 정리] - Protocol Buffer 개념 ~ Protocol Buffer 실습 2을 읽고 오길 바란다.
protocol buffer가 무엇이고 어떻게 사용하는 지를 알아야 이후부터 진행되는 내용을 정확히 이해할 수 있기 때문이다.
그리고 [Deep Learning/Tensorflow] - tf.gfile.GFile( )은 무엇일까도 관련된 내용이니 읽어둔다면 이해에 도움 될 것이다.
코드는 [ object_detection_tutorial.ipynb ]을 참고해 다음의 흐름으로 구현했다.
사용하고자 하는 모델 선택
선택된 모델의 frozen_inference_graph.pb 로드
그럼 사용자 선택 부분 부터 살펴보자.
1. 사용하고자 하는 모델 선택
API의 사용성을 올려보고자 추가로 작성했다.
우선 ./pretrained_model 경로에 이전 글에서 받은 faster_rcnn_resnet50 외에 두 개의 모델을 더 다운받아줬다.
이제 코드를 살펴보자.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 | import os import tensorflow as tf PRETRAINED_MODEL_PATH = './pretrained_model' file_list = os.listdir(PRETRAINED_MODEL_PATH) model_list = {} num_model = 1 for file in file_list: if 'tar.gz' in file: continue model_list[num_model] = file num_model += 1 print('\n[ model list ]') for key, value in model_list.items(): print(str(key) + '.', value) user_input = int(input('\n사용할 모델을 고르세요 : ')) model = model_list[user_input] | cs |
Line 5
: 지정된 경로에 있는 모든 파일들의 파일명을 반환해주는 함수다.
따라서 file_list에는 pretrained_model 폴더에 있는 모든 파일들의 파일명이 저장된다.Line 7 ~ 14
: tar.gz 파일을 제외한 파일명들로 딕셔너리를 만드는 과정이다.
사용자 입력과 연계해서 사용할 계획이기 때문에 key는 정수형 숫자로 잡았다.Line 16 ~ 22
: 딕셔너리를 'key. value'형태로 출력하고 사용자에게 입력을 받아 모델을 선택하는 과정이다.
2. 선택한 모델의 frozen_inference_graph.pb 로드
Tensorflow는 계산 그래프를 작성해서 session을 통해 실행해주는 구조다. Tensorflow를 다뤄본 사람이라면 무슨 말인지 이해할 거다.
이런 독특하면서도 복잡한 구조를 조금만 더 자세히 들여다봐보자.
지금까지는 그저 tensorflow의 함수들을 사용해 신경망을 설계할 목적으로 단순히 import tensorflow as tf 만 해서 사용해왔는데,
알아보니 import 하는 과정에서 내부적으로 많은 일들이 일어나는 것 같더라.
그리고 그 중 하나가 바로 default graph를 생성한다는 것이다.
tensorflow는 계산 그래프를 차곡차곡 그려나가다가 설계가 끝나면 session을 통해 실행시켜주는 흐름이다.
그래서 import tesnorflow as tf 다음에 X = tf.placeholder(tf.float32, [None, 784]) 와 같은 코드를 작성해나가기 시작하면
따로 언급을 안 하더라도 default graph에 자동적으로 그려지게 된다.
import 한 뒤에 default graph 가 생성되고, 이후로 변수나 오퍼레이터들을 생성할 때마다 default graph에 그려지는 것을 확인할 수 있다.
문제는 frozen_inference_graph.pb 에서 계산 그래프와 가중치값을 메모리에 올리는 과정이 위와 같은 형태가 아니란 점이다.
이 경우는 이미 완성된 계산 그래프 뭉탱이를 graph 객체에 올리는 방식이라 접근법이 다르다.
해결 방법으로는 두 가지가 있다.
default graph 객체에 frozen_inference_graph.pb의 계산 그래프를 바로 그려줘서 실행하는 방법
tf.Graph( )로 하나의 graph 객체를 만들어서 여기에 frozen_inference_graph.pb의 계산 그래프를 그려 실행하는 방법
나는 tf.Graph( )를 사용하는 방식으로 구현하도록 하겠다.
코드를 살펴보자.
24 25 26 27 28 29 30 31 32 33 34 35 36 37 | PATH_TO_FROZEN_GRAPH = PRETRAINED_MODEL_PATH + '/' + model + '/frozen_inference_graph.pb' detection_graph = tf.Graph() with detection_graph.as_default(): od_graph_def = tf.GraphDef() with tf.gfile.GFile(PATH_TO_FROZEN_GRAPH, 'rb') as f: serialized_graph = f.read() od_graph_def.ParseFromString(serialized_graph) tf.import_graph_def(od_graph_def, name = "") | cs |
Line 26
: 계산 그래프가 그려질 공간을 생성한다.Line 27
: detection_graph를 with 블록 내에서는 default graph로서 사용하겠다는 뜻이다.
따라서 Line 28 ~ 36 에서는 default graph가 detection_graph로 인식된다.Line 29
: frozen_inference_graph.pb 의 데이터를 deserialize 할 수 있는 객체다.Line 33 ~ 34
: frozen_inference_graph.pb 를 열어 serialized data를 읽은 후
od_graph_def 를 통해 deserialize를 수행한다.Line 36
: deserialize된 데이터를 default graph에 추가하는 과정이다. tf.import_graph_def( ) 가 이 역할을 수행한다.
with 블록 내에서는 default graph가 detection_graph이기 때문에
detection_graph에 frozen_inference_graph.pb 의 계산 그래프 데이터가 최종적으로 그려지게 된다.
다음은 모델을 선택해서 계산 그래프까지 그리는( = frozen_inference_graph.pb를 메모리에 올리는) 코드 전체이다.
[ run_inference_tf.Graph.py ]
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 | import os import tensorflow as tf PRETRAINED_MODEL_PATH = './pretrained_model' file_list = os.listdir(PRETRAINED_MODEL_PATH) model_list = {} num_model = 1 for file in file_list: if 'tar.gz' in file: continue model_list[num_model] = file num_model += 1 print('\n[ model list ]') for key, value in model_list.items(): print(str(key) + '.', value) user_input = int(input('\n사용할 모델을 고르세요 : ')) model = model_list[user_input] PATH_TO_FROZEN_GRAPH = PRETRAINED_MODEL_PATH + '/' + model + '/frozen_inference_graph.pb' detection_graph = tf.Graph() with detection_graph.as_default(): od_graph_def = tf.GraphDef() with tf.gfile.GFile(PATH_TO_FROZEN_GRAPH, 'rb') as f: serialized_graph = f.read() od_graph_def.ParseFromString(serialized_graph) tf.import_graph_def(od_graph_def, name = "") | cs |
다음 글에서는 메모리에 올린 계산 그래프를 실행시키는데 필요한 함수들을 만들어보도록 하겠다.
'Deep Learning > TF Object Detection API' 카테고리의 다른 글
2.1. Custom Dataset으로 TFRecord 파일 만들기 (0) | 2020.03.19 |
---|---|
2. Tensorflow Object Detection Model Retrain 방법에 대해 알아보자 (0) | 2020.03.13 |
1.5. draw_bounding_boxes 함수 설계 및 inference 결과 확인 (5) | 2019.07.30 |
1.4. run_inference_for_single_image 함수 설계 (0) | 2019.07.05 |
1.2. Pretrained model 다운로드 및 압축 풀기 (0) | 2019.07.02 |