1. Experiment
https://mz-moonzoo.tistory.com/6
저번 글에 이어서 1주일 정도 시간이 흘러서 그동안의 시행착오에 대해 정리해보고자 합니다. 우선 SOTA모델인 parseq를 활용했음에도 불구하고 드라마틱한 성능변화가 나타나지는 않았습니다. 그래서 여러가지 데이터셋 증강 기법과 파라미터 조정을 통해 성능 향상을 이끌어 냈습니다. 이제부터 실험과 실험 결과에 대해 간단히 작성하도록 하겠습니다.
Experiment Summary
1. baseline score -> 0.6563230797
-> model : Resnet+RNN+CTC Loss
Dataset : 대회 제공 train 데이터셋 (76888개) test_size=0.2 shuffle = True
2. parseq_try_1 -> 0.7218024825
-> model : parseq + img_size[32,128]
Dataset : 대회 제공 train 데이터셋 (76888개) test_size=0.2 shuffle = True
* 모델을 바꿨을 때 예상보다 낮은 성능 향상을 보여줌.
3. parseq_try_2 -> 0.7770282425
-> model : parseq + img_size[64,224]
Dataset : 대회제공 train 데이터셋(76888개) 학습 데이터 중 1글자 샘플들의 단어 사전이 학습/테스트 데이터의 모든 글 자를 담고 있으므로 학습 데이터로 우선 배치, 학습 데이터로 우선 배치한 1글자 샘플들과 2글자 이상의 학습 샘플을 concat하여 최종 학습 데이터로 사용 test_size = 0.2 shuffle= True
* 데이터셋의 구성과 이미지 사이즈를 조금 바꿨을 뿐인데 높은 성능 향상을 보여줌.
3. vitstr_try_1 -> 0.734349702
-> model : vitstr + img_size[64,224]
Dataset : 대회제공 train 데이터셋(76888개) 학습 데이터 중 1글자 샘플들의 단어 사전이 학습/테스트 데이터의 모든 글 자를 담고 있으므로 학습 데이터로 우선 배치, 학습 데이터로 우선 배치한 1글자 샘플들과 2글자 이상의 학습 샘플을 concat하여 최종 학습 데이터로 사용 test_size = 0.2 shuffle= True
* 다른 모델 테스트를 해봤지만 성능이 낮게 나와서 제외
4. parseq_try_3 -> 0.8313095881 (feat. open cv)
-> model : parseq + img_size[100,125] +파라미터 decode_ar : False, refine_iters : 0 설정 + rotation : 45 (random)
Dataset : 대회제공 train데이터셋의 이미지와 라벨로 아래의 CUT-MIX 기법을 적용해 train 데이터 augmentation 진행
1글자 샘플들의 단어 사전이 학습/테스트 데이터의 모든 글자를 담고 있으므로 학습 데이터로 우선 배치.
test_size = 0.2, shuffle = True
* 간단한 CUT-MIX기법으로 10만건 정도 데이터셋을 증강시켰을 때 높은 성능 향상을 보여줌.
5. parseq_try_4 -> 0.8293308149 (feat. imgaug, straug, timm)
-> model : parseq + img_size[100,125] +파라미터 decode_ar : False, refine_iters : 0 설정 + rotation : 45 (random)
Dataset : 대회제공 train데이터셋의 이미지와 라벨로 아래의 CUT-MIX 기법을 적용해 train 데이터 augmentation 진행.
Imgaug 라이브러리와 timm 라이브러리의 auto_augment로 커스터마이징 데이터 증강 기법을 적용해 데이터 증강
1글자 샘플들의 단어 사전이 학습/테스트 데이터의 모든 글자를 담고 있으므로 학습 데이터로 우선 배치.
총 170만건의 데이터 생성
test_size = 0.2, shuffle = True
* 데이터를 증강시킬 때마다 꾸준한 성능 향상을 보여줘서 데이터를 최대한 증강시키고 학습을 진행했지만 오히려 성능이 떨이지는 것을 보아 데이터의 품질과 모든 단어를 학습해야할 필요가 있음.
6. parseq_try_5-> 0.8947202734 (feat. Synthtiger)
-> model : parseq + img_size[100,125] +파라미터 decode_ar : False, refine_iters : 0 설정 + rotation : 45 (random)
Dataset : 대회제공 train데이터셋의 이미지와 라벨로 아래의 CUT-MIX 기법을 적용해 train 데이터 augmentation 진행.
Synthtiger을 사용해 여러 한국어 폰트를 적용해 데이터 생성.
test_size = 0.2, shuffle = True
* 데이터 셋의 품질이 중요하고 다양한 글자를 학습시키는 것이 중요하다 사실을 확인함.
하지만 대회 규칙에서 폰트를 적용해 데이터를 생성하는 것은 안된다는 것을 뒤늦게 알아서 사용하지는 못함.
7. parseq_try_6 -> ?????? (feat. ESRGAN)
-> model : parseq + img_size[100,125] +파라미터 decode_ar : False, refine_iters : 0 설정 + rotation : 45 (random)
Dataset : 대회제공 train데이터셋의 이미지와 라벨로 아래의 CUT-MIX 기법을 적용해 train 데이터 augmentation 진행.
이후 ESRGAN을 활용해 Noise를 제거해 데이터 증강에 활용.
* 하지만 대회 시간상의 문제로 성능 테스트를 하지 못함. 더 깔끔한 Text Data를 학습할 수 있어 성능 향상을 기대할 수 있다고 생각함. 그리고 이와 언어모델을 활용한다면 더 좋은 성능 향상을 할 수 있을 것이라 생각함.
문제 탐색
리더보드 상위 10% score를 보면 성능이 0.9가 넘는 사람들이 대부분입니다. 그렇기 때문에 아직 성능 향상을 위해 여러가지 시도를 할 필요가 있다고 생각했습니다. 그래서 parseq에서 모델 yaml의 이름만 살짝 변경해줘도 여러가지 모델을 사용할 수 있어 vitstr,trba모델을 돌려보며 성능 테스트를 해봤습니다.
trba의 경우 val_accuracy가 0.73으로 낮은 score를 보여줘서 제외를 했는데 vitstr, parseq 모두 모델의 epochs가 10정도만 넘어가도 val_accuracy가 0.9이상으로 올라가고 40epochs를 돌았을 때는 0.99의 성능을 기록하고 있습니다. 하지만 제출 결과 score는 0.7~0.77 사이로 val_accuracy와 큰 성능 차이를 보여주고 있습니다.
모델만으로는 성능 향상이 힘들다!
문제 발견
val_accuracy가 높게 나왔지만 public score는 낮게 나오는 이유가 무엇일까 생각을 해봤습니다. 그 결과 모델만으로는 성능 향상이 힘들고 학습 데이터셋이 중요하다는 결론을 내렸습니다. 기존의 학습 데이터는 6~7만개의 데이터로 train을 진행하고 validation 데이터로 6~9천개 정도의 데이터만 사용하기때문에 학습하지 못한 글자와 단어가 있을 것입니다.
이 대회에서는 Pretrained모델을 사용할 수는 있지만 한국어로 Pretrained된 모델이 없거나 외부 데이터로 학습된 모델이 대부분이기 때문에 규칙에 의해 사용할 수 없어 학습 데이터셋의 중요성이 더 크다고 생각했습니다.
학습 데이터를 최대한 늘리는 것이 중요하다!
해결책
학습 데이터를 최대한 늘리는 것이 중요하다고 생각을 했지만 외부 데이터를 사용할 수 없는 대회였기 때문에 dataset에 적용할 수 있는 여러 augment기법을 적용하고자 했습니다.
- 현실에서는 충분히 큰 양의 공개된 라벨 데이터셋을 찾기 어렵기 때문에 대부분의 연구에서 합성 데이터 사용
straug
https://github.com/roatienza/straug
현실에서 나타나는 다양한 text property에 대응하는 36가지 augmentation fuctions의 모음인 STRAug 활용
CUT_MIX
https://dacon.io/competitions/official/236042/codeshare/7374?page=1&dtype=recent
DACON 코드 공유에 올려주신 CUT-MIX 기법을 사용해 Data Augmentation.
Parseq_augmentation.py
https://github.com/baudm/parseq/blob/main/strhub/data/augment.py
Parseq자체 내장 함수로 augmentation이 가능하기 때문에 파라미터를 조정하며 활용.
Synthtiger
https://github.com/clovaai/synthtiger
Text image augmentation이 가능한데 문자의 조합과 폰트 등 커스터마이징을 진행하면 다양한 이미지 데이터를 생성할 수 있습니다. 추후에 논문 리뷰와 구현까지 진행해 업로드 하도록 할 예정입니다.
ESRGAN
https://github.com/xinntao/Real-ESRGAN
GAN으로 Noise를 없애는 방법으로 데이터셋 증강에 활용할 수 있고 양질의 Text Data 학습이 가능하다는 장점이 있음.
2. Review
첫 OCR 대회를 무사히 마쳤습니다. 최종 순위는 아직 나오지 않았지만 상위 10%안에는 들 수 있었습니다.
OCR 대회를 진행하면서 OCR Task에 맞는 모델들을 찾아보고 직접 활용해 테스트 해봤습니다.
그리고 성능을 높이기 위해 증강 기법, 언어모델 사용 등 여러 기법을 적용해보면서 OCR Task에 흥미를 갖게 됐습니다.
하지만 첫 대회다보니 아직 미숙한 점이 많아 조사를 하고 실험을 하는데 시간을 너무 많이써서 좀 더 성능 향상을 이끌어 내지 못해서 아쉬웠습니다. 앞으로 좀 더 논문을 찾아보고 공부를 하면서 성능이 좋은 OCR 모델을 만들어보고 싶습니다.
(2023-01-16 수정) 대회 종료 시점으로 깃허브 업로드 완료했습니다.