ddps-lab / edge-inference

Evaluation of inference model performance on edge devices
Apache License 2.0
2 stars 3 forks source link

tpu 환경에서 image classification 추론시 accuarcy 수치 이슈 #31

Closed jungae-park closed 2 years ago

jungae-park commented 2 years ago

https://github.com/ddps-lab/research-issues/issues/45

입력 형식을 해결하여 tpu 환경에서 dtype이 모두 int8인 tfrecord imagenet dataset, edgetpu 모델을 사용한 추론 결과를 아래와 같이 확인하였습니다.

***** TF-lite matric *****
user_batch_size = 1
accuracy = 0.001
model_load_time = 3.132760524749756
dataset_load_time = 3.074784755706787
inference_time = 41.50337839126587
inference_time(avg) = 0.017514058351516724
IPS = 20.959311305960835
IPS(inf) = 57.09698916889812

정확도 수치가 이상하여 디버깅을 진행하고 있습니다.

kmu-leeky commented 2 years ago

오케이. 그러면 지금은 이미지 관련 모델들은 coral 공홈에서 제공해주는걸 사용하는거고, validation 이미지의 경우 imagenet 의 원래 파일이 32비트였는데 동작하지 않아서 이걸 8비트로 변환한 후 동작은 성공 시켰는데 정확도가 낮은거지?

IPS 를 보면 다른 장비와 비교해보면 어떤것 같아?

jungae-park commented 2 years ago

공홈에서 제공해주는 int8 모델을 사용하였고, 데이터를 모델의 int8과 동일하게 맞춰준 후 동작을 시켰을 때 정확도가 낮았습니다. 같은 mobilenet v1의 모델 기준으로 다른 장비와 IPS를 비교해보면 초당 처리하는 이미지 개수가 더 많은 것 같습니다. [coral tpu] IPS = 20.959311305960835 IPS(inf) = 57.09698916889812 [nvidia jetson] image

kmu-leeky commented 2 years ago

엄청 많이 높은것 같네. 이게 혹시 입력을 변환해서 그런것일수도 있겠네. 성능차이가 많이 난다면 이유도 같이 보도록 하자.

jungae-park commented 2 years ago

[mobilenet v2]

***** TF-lite matric *****
user_batch_size = 1
accuracy = 0.906
model_load_time = 3.1900439262390137
dataset_load_time = 4.84524130821228
inference_time = 251.73118042945862
inference_time(avg) = 0.24620095443725587
IPS = 3.849590473185798
IPS(inf) = 4.061722678068859

[inception v3]

***** TF-lite matric *****
user_batch_size = 1
accuracy = 0.919
model_load_time = 3.4438836574554443
dataset_load_time = 3.8864810466766357
inference_time = 1854.731003522873
inference_time(avg) = 1.8491149649620056
IPS = 0.5370389898402086
IPS(inf) = 0.540799257454794

-> mobilenet v1 모델과 다르게 정확도가 높게 측정되고, IPS의 경우 다른 장비와 비슷하게 측정되는 것을 확인 -> 따라서 mobilnet v1 모델에서 정확도가 낮은 것이 입력형식이 int8이여서 그런 것인 것 같고, 실제값과 예측값의 형식이 달라서 정확도 계산에 문제가 생긴 것이 아닌가 하는 생각에 추가로 확인하고 있습니다.

kmu-leeky commented 2 years ago

정애야.정리를 해보면

이게 맞는거지? 그렇다면 조금 이상한대.. 뭔가 실험 환경 설정이 잘 안된것 같기도하고.. coral 에서 제공해주는 같은 모델인데 입력에 따른 차이가 저렇게 난다는게.

그리고 위에서 공유해준 정확성이 떨어지는 문제는 읽어보니 coral 에서 제공해주는 모델을 사용시에는 정확도가 높은데, 본인이 직접 compile 을 하면 낮아진다는것 같아. 정애가 사용한건 컴파일이 된거지 않아? 아니면 컴파일이 된 모델에 "edgetpu_compiler" 이건 또 실행을 해줘야 하는거야?

jungae-park commented 2 years ago

네 정리해주신 내용이 맞습니다. 저도 coral에서 제공해주는 같은 모델인데, 입력에 차이가 있는것이 이상하다고 생각합니다. 실험 환경 설정 및 다른 세부 사항들을 다시 살펴봐야 할 것 같습니다.

그리고 공유드린 정확성 떨어지는 것에 대한 내용은 저런 경우도 있었다는걸 참고하려고 남겨두었습니다. 저희는 공홈에서 edgetpu_compiler를 실행하여 제공한 모델이라 따로 컴파일 할 필요는 없습니다.

내용을 천천히 살펴보고 특이사항이 있었는지 확인하여 업데이트하겠습니다.

kmu-leeky commented 2 years ago

공홈에서 제공해주는 모델인데 어떤게 32비트, 어떤건 8비트 입력에서 에러가 난다면 우리가 작성한 코드에 뭔가 문제가 있을 확률이 높아보이네. 혹시 공홈에서 작성한 모델을 그대로 동작시키는 코드는 못찾았어? 그걸 그대로 사용하는게 좋을것 같아.

jungae-park commented 2 years ago

공홈에서 제공하는 간단한 image classification 코드가 있습니다. https://github.com/google-coral/tflite/blob/master/python/examples/classification/classify_image.py 이걸 참고해서 다시 살펴보겠습니다.

jungae-park commented 2 years ago

모델에 따라 입력 형식을 다르게 해야 동작이 되는 이슈가 생겨, 아래와 같이 환경 설정 및 세부사항에 대해 다시 살펴보았습니다.

1) 공홈 모델 다시 가져와서 실행 https://coral.ai/models/image-classification/ 환경 설정에는 문제가 없었고, 모델이 이상한 듯하여 공홈에서 다시 모델 확인 후 다운로드 (확인해보니 TF1인 모델을 사용하고 있었음) image

kmu-leeky commented 2 years ago

오케이. 정애야. 내가 이해를 한걸 정리를 하면.

전반적으로 coral 에서 제공해주는 코드를 사용해서 해보자고 했는데, 아직 어떤 상황인지 잘 그려지지 않네. 얼른 마쳐서 다음 단계로 넘어가야 할텐데. 어떤 문제 해결에 많은 시간이 소요되는지 이야기를 해볼 필요가 있겠다.

jungae-park commented 2 years ago
  1. 이전에 사용한 mobilenet v1, v2 모델이 공홈에서 TF1으로 제공 된 모델을 사용 했던 것이어서 이슈가 있었던 것 같습니다. 그래서 공홈에서 TF2로 제공되는 mobilenet v1, v2 모델을 다시 가져와 사용하였고, 입력 형식은 int8로 동작합니다. 하지만 현재 accuracy가 0.01로 이슈가 있는 상태입니다. 이는 공홈에서 제공해주는 코드 https://github.com/google-coral/tflite/blob/master/python/examples/classification/classify_image.py 를 다시 살펴보고 정확도 문제를 해결하고자 합니다.

  2. dataset을 tfrecord로 변환하는 것은 아래 tfrecord 변환 코드를 활용해서 이전에 진행을 했었습니다. (공홈 추론 코드, 정애 코드와 상관 없음) https://github.com/kmonachopoulos/ImageNet-to-TFrecord/blob/master/build_imagenet_data.py 저는 이 코드에서 float32에서 int8로 변형해서 tfrecord를 생성할 수 있다고 생각하였는데, 이 코드에서는 label과 image를 한번에 묶는 것만 진행되고 있었습니다.

실제로 tfrecord를 float32에서 int8로 입력형식을 변환하는 것은 https://github.com/ddps-lab/edge-inference/blob/main/CNN/ic_inference_edgetpu.py 정애 추론 코드에서 43-67라인, 119라인 입니다. tfrecord dataset을 가져와 이미지를 float32로 읽어 오고, 모델에 넣어 추론을 할 때 int8로 입력 형식을 변경하여 추론 하는 형태였습니다. 119라인은 현재 아래와 같이 변경하여 사용하고 있습니다.

input_data = tf.cast(validation_ds, tf.uint8)

이렇게 tfrecord dataset의 입력 형식이 어디 부분에서 변환되어 추론에 들어가게 되는지 살펴보았습니다. 정확도 이슈와 관련이 있는 것 같아 언급하였던 것이고, 공홈에서 제공해주는 추론 코드의 데이터 입력 형식과 비교하여 살펴보고 있습니다.

  1. inception v3 모델의 경우 공홈에서 TF1으로 작성된 모델만 제공하여 사용할 수가 없고, 따로 TF2의 inception v3 모델을 tflite로 convert후에 edge 컴파일러로 컴파일하여 사용하는 방향으로 진행하고 있었습니다. 컴파일은 성공하였지만, 입력 형식이 float 32이어야 하는 이슈가 똑같이 발생하였습니다. 하지만 이는 tflite로 convert 할 때 int8로 convert를 하고 edge 컴파일로 컴파일을 한 모델을 사용하면 해결이 될 것 같습니다. (현재 모델은 tflite로 convert 할 때 float32로 진행 되었고, 저는 edge 컴파일러가 int8로 변환해주는 것으로 생각했었습니다.)
kmu-leeky commented 2 years ago

정리하면 coral 홈페이지에서 이전에는 TF1 모델을 제공해줬는데 지금은 TF2 모델을 제공해준다는거지? 공홈에서 TF1 버전과 TF2 버전을 선택해서 받을수 있는거야?

데이터셋을 계속 변환하지 말고 그냥 coral 에서 제공해주는 코드랑 데이터셋을 그대로 사용하는게 나을것 같은데. 지금 같은 문제가 계속 발생하니까 제공해주는 코드를 실행해서 문제가 어디에 있는지 봐야할것 같아. 우리 코드는 생각하지말고 그냥 coral 홈페이지에서 제공해주는 코드와 데이터셋을 활용할수는 없는거야? 거기서부터 디버깅을 시작할수 있을것 같아.

Inception v3 의 경우 코랄 홈페이지에서 TF1 만을 제공해준다는거지? 해당 홈페이지를 보면 TF1 과 TF2 에 대한 언급은 따로없는것 같아서. InceptionV3 의 경우 tflite 및 edge 컴파일을 우리가 진행했으니 입력에 대한 이슈가 있을수도 있겠네. 시도할만한게 있을것 같으니 한번 진행해보자.

jungae-park commented 2 years ago

공홈에서 아래 이미지와 같이 모델 종류, dataset, input size, TF version, latency, accuracy, model size 형식으로 모델을 다운로드 할 수 있었습니다. 그래서 TF2 버전으로 모델을 다운로드 받을 수 있었습니다. image

coral에서 제공해주는 데이터셋은 tfrecord 형식이 아닌 원본 이미지 데이터셋이며 코드도 원본 이미지 데이터셋을 추론하기 위해 작성된 코드입니다. (공홈 간단한 코드 실행은 정상 작동 하였습니다.) 간단히 새의 이미지 한 장을 추론하는 코드입니다. image

공홈 코드를 활용해서 입력형식, 정확도 문제를 해결할 수 있을지 더 살펴봐야할 것 같습니다.

inception v3 모델은 int8 형식으로 tflite로 convert하고 edgetpu용으로 컴파일을 진행해서 추론 해보겠습니다.

kmu-leeky commented 2 years ago

페이지에 TF 버전 컬럼이 있구나. 해당 내용을 참조하면 되기는 하겠다.

입력의 경우 tfrecord 를 사용하지 않기에 우리가 비교했던 다른 장비와 직접적인 비교가 어려울수 있겠네. 현재 MobileNet V1, V2 의 문제는 tfrecord 를 사용시 정확도가 낮은게 문제니까 원본 이미지를 사용해서 (코랄 홈페이지에서 제공해주는) 보여지는 정확도는 높은지를 우선 봐야겠네. 그리고 원본 이미지를 처리하는 성능과 정확도는 낮지만 tfrecord 를 처리하는 속도를 비교해보면, 처리속도에 대한 이해는 가능할것 같네. 만약에 원본이미지로는 잘 진행이 된다면 지금 우리가 가지고 있는 tfrecord 로 변환하는 방법이 코랄에서 동작하는 모델을 동작시키는 모델과는 달라서일수도 있겠다.

우선 MobileNetV1, V2 에서 tfrecord 가 아닌 원본 이미지를 가지고 처리시에 정확도와 처리 속도를 측정해보자.

jungae-park commented 2 years ago

네 mobilenet v1, v2 모델에서 원본 이미지를 처리할 때 정확도와 처리 속도를 확인해보겠습니다. (공홈 코드 참고)

jungae-park commented 2 years ago

우선 공홈에서 제공하는 원본 이미지 (imagenet)은 다운을 받을 수 없는 상태이므로, 저희가 가지고 있는 imagenet 원본 이미지를 가지고 추론을 진행해보았습니다. 모델은 공홈에서 제공해주는 mobilenet v1, v2를 사용하여 추론 시간과 정확도를 측정해보았습니다.

같은 원본 이미지 하나를 두 모델에서 처리 할 때 측정된 값은 아래와 같습니다. [mobilenet v1]

root@b63165540762:/edge-inference/CNN/test# python3 classify_image.py --model ./tf2_mobilenet_v1_1.0_224_ptq_edgetpu.tflite --labels ./imagenet_metadata.txt --input ./ic-imagenet-dataset/n04239074/ILSVRC2012_val_00010499.JPEG
----INFERENCE TIME----
Note: The first inference on Edge TPU is slow because it includes loading the model into Edge TPU memory.
142.6ms
15.1ms
15.4ms
15.7ms
14.8ms
-------RESULTS--------
n01629276   salamander: 0.69141

[mobilenet v2]

root@b63165540762:/edge-inference/CNN/test# python3 classify_image.py --model ./tf2_mobilenet_v2_1.0_224_ptq_edgetpu.tflite  --labels ./imagenet_metadata.txt --input ./ic-imagenet-dataset/n04239074/ILSVRC2012_val_00010499.JPEG
----INFERENCE TIME----
Note: The first inference on Edge TPU is slow because it includes loading the model into Edge TPU memory.
128.4ms
15.7ms
15.7ms
15.7ms
15.9ms
-------RESULTS--------
n01629276   salamander: 0.75391

공홈에서 제공하는 accuracy 값과 비교하였을 때 비슷하게 측정 된 것 같아 여러개의 이미지 추론도 추가로 진행해보려고 합니다. (IPS 추가 측정) image

원본 이미지와 공홈에서 제공한 모델과 추론 코드를 사용하여 결과값을 확인하였을 때 정확도가 높다면 tfrecord로 추론할때는 모델이 이미지의 입력형식을 인식하는 부분에서 문제가 있는게 맞는 것 같습니다.

kmu-leeky commented 2 years ago

응 정애야. 이런식으로 가장 간단한 설정을 시작으로 (홈페이지에서 제공해주는 모델+데이터셋) 조금씩 환경을 복잡하게 하면서 성능 차이가 나는 부분을 발견하는게 좋은 시도인것 같아. 처리 성능 관련해서는 결과가 나온게 있어? 공홈에서 제공해주는 방식으로 tfrecord 사용안할때 추론시간. 얼핏보면 15msec 정도인걸보니 최대 초당 6~7개 정도 처리가 될것 같은데?

jungae-park commented 2 years ago

원본이미지 1000장에 대해 공홈에서 제공해주는 모델, 코드를 사용하여 성능을 아래와 같이 측정해보았습니다.

[mobilenet v1]

***** TF-lite matric *****
accuracy = 0.70559765625
model_load_time = 3.1259117126464844
dataset_load_time = 1.259901762008667
inference_time = 51.5816867351532
inference_time(avg) = 0.017351717145415023
IPS = 6.03865541842746e-07
IPS(inf) = 57.631183796944136

[mobilenet v2]

***** TF-lite matric *****
accuracy = 0.70559765625
model_load_time = 3.125209093093872
dataset_load_time = 1.0419745445251465
inference_time = 51.86566948890686
inference_time(avg) = 0.017398215427529066
IPS = 6.038654780200787e-07
IPS(inf) = 57.47715931932349

기존 tfrecord dataset의 accuracy를 계산 할 때에는 모든 데이터에 대한 실제 라벨과 예측 라벨을 비교한 뒤, 정확도 계산하는 형태로 구했습니다.

accuracy = np.sum(np.array(real_labels) == np.array(pred_labels))/len(real_labels)

현재는 공홈에서 제공한 코드에 의하면 원본 이미지 1000장 (1000개의 class별로 1장씩 구성된 데이터셋)을 클래스별로 정확도를 계산하는 형태입니다.

-------RESULTS--------
n01527617   lark: 0.33984
-------RESULTS--------
n01651285   chameleon tree frog: 0.92578
-------RESULTS--------
n01482330   shark: 0.80078
-------RESULTS--------
n01318894   pet: 0.34766
-------RESULTS--------
n01517565   ratite, ratite bird, flightless bird: 0.94141
-------RESULTS--------
n01405007   fucus: 0.90234
-------RESULTS--------
n01554448   woodhewer, woodcreeper, wood-creeper, tree creeper: 0.98047
-------RESULTS--------
n01314781   creepy-crawly: 0.98047
-------RESULTS--------
n01582220   magpie: 0.46094

그래서 최종 정확도를 모든 클래스의 평균 정확도로 계산해도 괜찮은지 궁금합니다. 계산을 하였을 때, mobilnet v1과 v2 모델의 정확도가 공홈에서 제공하는 정확도와 비슷 한 것은 확인하였습니다.

IPS 값은 tfrecord 데이터셋을 사용할 때와 비교하면, IPS는 좀 떨어졌는데, IPS(inf)값은 비슷합니다.

kmu-leeky commented 2 years ago

응 정애야 잘했다. 우선 정애가 서술한것을 기반으로 하면 우리가 만든 tfrecord 를 사용하지 않고, 코랄이 공식적으로 제안하는 코드를 사용하면 정확도는 차이가 나지만 처리 속도는 비슷한거지? 그렇다면 우리가 내릴수 있는 결론은 우리가 정확도를 신경써서 진행한다면 꼭 tfrecord 를 제대로 해야겠지만, 처리속도를 위주로 본다면 어느정도 정확도가 낮은건 용납될것 같아. 처리속도는 비슷하니까.

그렇게 결정을 내리기 전에 몇가지 궁금한점은

IPS = 6.038654780200787e-07 IPS(inf) = 57.47715931932349

IPS 는 왜 10^-7 이 붙는거야? 내가 이해하기에는 IPS 는 모델을 로딩하는 시간 포함, IPS(inf) 는 순수 추론 시간으로 이해했는데, IPS 값이 너무 낮은것 같은데, 왜 그런건지 확인 부탁해. 어떻게 계산이 되는지를 공유해주면 좋을것 같아.

jungae-park commented 2 years ago
kmu-leeky commented 2 years ago

모든걸 다 완벽하면 하면 좋겠지만,그렇게되면 시간이 너무 오래걸리니까.. 지금 여기서 우리 촛점은 모델의 정확도보다는 처리 성능이기도 해서, 가능하면 원본 이미지랑 tfrecord 로 둘다 돌려보고 처리 성능에 큰 차이가 없다면 둘중 하나를 사용하도록 하자. 정확도는 너무 신경쓰지말고. 그리고 IPS 의 경우는 지금까지 다른 경우에도 다 문제가 있는 방식으로 계산이 된거였지?

jungae-park commented 2 years ago

아닙니다. IPS는 현재 실험에서만 잘 못 계산 된 것입니다. 제가 dataset을 로드해오는 과정에서 문제가 있었던 것 같습니다. 다시 살펴보고 업데이트 하겠습니다.

jungae-park commented 2 years ago

IPS를 다시 계산 하여 아래와 같은 값을 얻었습니다. [mobilenet v1]

***** TF-lite matric *****
accuracy = 0.7466875
model_load_time = 3.136709690093994
dataset_load_time = 0.6347105503082275
inference_time = 49.95246148109436
inference_time(avg) = 0.01541767023713328
IPS = 18.61369595711602
IPS(inf) = 64.86064266645889

[mobilenet v2]

***** TF-lite matric *****
accuracy = 0.70559765625
model_load_time = 3.1174354553222656
dataset_load_time = 1.0107810497283936
inference_time = 50.1428017616272
inference_time(avg) = 0.01652078828914091
IPS = 18.42604085823824
IPS(inf) = 60.52979933513817

IPS 계산은 아래와 같이 계산하였습니다.

  print('IPS =', 1000 / (model_load_time + dataset_load_time + inference_time))
kmu-leeky commented 2 years ago

오케이. IPS 계산 makes sense. iicws 2019 논문 중 edge 에서 dnn 성능 비교한 논문 (Georgia Tech) 의 초반에보면 FLOPS/Model size (parameter size) 를 비교하던데, 해당 내용이 IPS 와 IPS(inf) 차이에 영향을 미칠것 같네. 우리 실험에서도 해당 값들을 계산해보면 좋을것 같아. 아마도 수빈 재강이 가 지금 작업하는 논문에서도 필요할 내용일것 같기도 해.

jungae-park commented 2 years ago

네 교수님 iicws 2019 논문에서 FLOPS/Model size (parameter size) 계산한 내용을 살펴보고, 저희 실험에서도 계산을 해보고 IPS와 IPS(inf) 차이를 살펴보겠습니다.

jungae-park commented 2 years ago

해당 이슈는 해결되어 close하겠습니다.