ํ๊ตญ์ด ์๋ ์์ฑ ์ธ์ ํ๊ฐ๋ฅผ ์ํ ์ ์ฌ๋ ์ธก์ ํจ์ ํจํค์ง
์ด ์ ์ฅ์์๋ Amazon Transcribes์ ๊ฐ์ ํ๊ธ ๋ฌธ์ฅ ์ธ์๊ธฐ์ ์ถ๋ ฅ ์คํฌ๋ฆฝํธ์ ๋ฑ๋ง ์ค๋ฅ์จ(CER), ๋จ์ด ์ค๋ฅ์จ(WER)์ ๊ณ์ฐํ๋ ๊ฐ๋จํ Python ํจํค์ง๊ฐ ํฌํจ๋์ด์์ต๋๋ค. STT(speech-to-text) API์ ์ค์ (Ground truth)๋ฌธ์ฅ๊ณผ ๊ฐ์ค(hypothesis or transcribe)๋ฌธ์ฅ ์ฌ์ด์ ์ต์ ํธ์ง๊ฑฐ๋ฆฌ๋ฅผ ๊ณ์ฐํฉ๋๋ค. ์ต์ํธ์ง๊ฑฐ๋ฆฌ๋ Dynamic Programing ๊ธฐ๋ฒ ์ค Levenshtein์ ์ฌ์ฉํ์ฌ ๊ณ์ฐ๋ฉ๋๋ค.
๋ฌธ์ ์ค๋ฅ์จ(CER/WER)์ ์๋ ์์ฑ ์ธ์ ์์คํ ์ ์ฑ๋ฅ์ ๋ํ ์ผ๋ฐ์ ์ธ ๋ฉํธ๋ฆญ์ ๋๋ค. CER์ WER(๋จ์ด ์ค๋ฅ์จ)๊ณผ ์ ์ฌํ์ง๋ง ๋จ์ด ๋์ ๋ฌธ์์ ๋ํด ์๋ํฉ๋๋ค. ์์ธํ ๋ด์ฉ์ WER ๋ฌธ์๋ฅผ ์ฐธ์กฐํ์ญ์์ค.[1] ๋ฌธ์ ์ค๋ฅ์จ์ ๋ค์๊ณผ ๊ฐ์ด ๊ณ์ฐํ ์ ์์ต๋๋ค.
CER(WER) = (S + D + I) / N = (S + D + I) / (S + D + I + C)
- S : ๋์ฒด ์ค๋ฅ, ์ฒ ์๊ฐ ํ๋ฆฐ ์ธ์(uniliteral)/๋จ์ด(word) ํ์
- D : ์ญ์ ์ค๋ฅ, ์ธ์/๋จ์ด์ ๋๋ฝ ํ์
- I : ์ฝ์ ์ค๋ฅ, ์๋ชป๋ ์ธ์/๋จ์ด๊ฐ ํฌํจ๋ ํ์
- C : Ground truth์ hypothesis ๊ฐ ์ฌ๋ฐ๋ฅธ ์ธ์/๋จ์ด(๊ธฐํธ)์ ํฉ๊ณ, (N - D - S)
- N : ์ฐธ์กฐ์(Ground truth) ์ธ์/๋จ์ด ์
CER์ ์ถ๋ ฅ์ ํนํ ์ฝ์ ์๊ฐ ๋ง์ ๊ฒฝ์ฐ ํญ์ 0๊ณผ 1 ์ฌ์ด์ ์ซ์๊ฐ ์๋๋๋ค. ์ด ๊ฐ์ ์ข ์ข ์๋ชป ์์ธก๋ ๋ฌธ์์ ๋ฐฑ๋ถ์จ๊ณผ ์ฐ๊ด๋ฉ๋๋ค. ๊ฐ์ด ๋ฎ์์๋ก ASR ์์คํ ์ ์ฑ๋ฅ์ด ํฅ์๋๊ณ CER์ด 0์ด๋ฉด ์๋ฒฝํ ์ ์์ ๋๋ค. ์ด ํจ์์์๋ insertion์ ๋ฐ๋ฅธ ์ค๋ฅ๊ฐ ์ด๊ณผ์ ๋ํด normalized error rate์ผ๋ก ์ ์ฉํ์ต๋๋ค.[2]
CER์ ์๋ ์์ฑ ์ธ์(ASR) ๋ฐ ๊ดํ ๋ฌธ์ ์ธ์(OCR)๊ณผ ๊ฐ์ ์์ ์ ๋ํ ๋ค์ํ ๋ชจ๋ธ์ ๋น๊ตํ๋ ๋ฐ ์ ์ฉํ๋ฉฐ, ํนํ ์ธ์ด์ ๋ค์์ฑ์ผ๋ก ์ธํด WER์ด ์ ํฉํ์ง ์์ ๋ค๊ตญ์ด ๋ฐ์ดํฐ ์ธํธ์ ๊ฒฝ์ฐ์ ์ ์ฉํฉ๋๋ค. CER ๊ฐ์ ๊ฒฝ์ฐ, ๋ฒ์ญ ์ค๋ฅ์ ํน์ฑ์ ๋ํ ์ธ๋ถ ์ ๋ณด๋ฅผ ์ ๊ณตํ์ง ์์ผ๋ฏ๋ก ์ค๋ฅ์ ์ฃผ์ ์์ธ์ ์๋ณํ๊ณ ์ฐ๊ตฌ ๋ ธ๋ ฅ์ ์ง์คํ๊ธฐ ์ํด์๋ ์ถ๊ฐ ์์ ์ด ํ์ํฉ๋๋ค. ๋ํ ๊ฒฝ์ฐ์ ๋ฐ๋ผ ์๋ณธ ER์ ๋ณด๊ณ ํ๋ ๋์ ์ค์ ์๋ฅผ ํธ์ง ์์ ์(I + S + D)์ C(์ ํํ ๋ฌธ์ ์)์ ํฉ์ผ๋ก ๋๋ ์ ๊ทํ๋ ER์ด ํ์ํฉ๋๋ค. ๊ทธ ๊ฒฐ๊ณผ 0โ100% ๋ฒ์์ ์ํ๋ CER ๊ฐ์ด ์์ฑ๋ฉ๋๋ค.
์ฌ์ฉ๋ฐฉ๋ฒ
๊ฐ์ฅ ๊ฐ๋จํ ์ฌ์ฉ ์ฌ๋ก๋ ๋ ๋ฌธ์์ด ๊ฐ์ ํธ์ง ๊ฑฐ๋ฆฌ๋ฅผ ๊ณ์ฐํ๋ ๊ฒ์ ๋๋ค.
pip install nlptutti
CER
import nlptutti as metrics
refs = "์ํคํํธ"
preds = "์ํคํ์ณ"
# prints: [cer, substitutions, deletions, insertions] -> [CER = 1 / 4, S = 1, D = 0, I = 0]
import nlptutti as metrics
refs = "์ ์ด ์ฐจ ์ธ๊ณ ๋์ ์ ์ธ๋ฅ ์ญ์ฌ์ ๊ฐ์ฅ ๋ง์ ์ธ๋ช
ํผํด์ ์ฌ์ฐ ํผํด๋ฅผ ๋จ๊ธด ์ ์์ด์๋ค."
preds = "์ ์ด์ฐจ ์ธ๊ณ๋์ ์ ์ธ๋ฅ ์ญ์ฌ์ ๊ฐ์ฅ๋ง์ ์ธ๋ช
ํผํด์ ์ฌ์ฐํผํด๋ฅผ ๋จ๊ธด ์ ์์ด์๋ค."
result = metrics.get_cer(refs, preds)
cer = result['cer']
substitutions = result['substitutions']
deletions = result['deletions']
insertions = result['insertions']
# prints: [cer, substitutions, deletions, insertions] -> [CER = 0 / 34, S = 0, D = 0, I = 0]
WER
import nlptutti as metrics
refs = "๋ํ๋ฏผ๊ตญ์ ์ฃผ๊ถ ๊ตญ๊ฐ ์
๋๋ค."
preds = "๋ํ๋ฏผ๊ตญ์ ์ฃผ๊ถ๊ตญ๊ฐ ์
๋๋ค."
result = metrics.get_wer(refs, preds)
wer = result['wer']
substitutions = result['substitutions']
deletions = result['deletions']
insertions = result['insertions']
# prints: [wer, substitutions, deletions, insertions] -> [WER = 2 / 4, S = 1, D = 1, I = 0]
CRR
import nlptutti as metrics
refs = "์ ์ด ์ฐจ ์ธ๊ณ ๋์ ์ ์ธ๋ฅ ์ญ์ฌ์ ๊ฐ์ฅ ๋ง์ ์ธ๋ช
ํผํด์ ์ฌ์ฐ ํผํด๋ฅผ ๋จ๊ธด ์ ์์ด์๋ค."
preds = "์ ์ด์ฐจ ์ธ๊ณ๋์ ์ ์ธ๋ฅ ์ญ์ฌ์ ๊ฐ์ฅ๋ง์ ์ธ๋ช
ํผํด์ ์ฌ์ฐํผํด๋ฅผ ๋จ๊ธด ์ ์์ด์๋ค."
result = metrics.get_cer(refs, preds)
crr = result['crr']
substitutions = result['substitutions']
deletions = result['deletions']
insertions = result['insertions']
# prints: [crr, substitutions, deletions, insertions] -> [CRR = 1 - (0 / 34), S = 0, D = 0, I = 0]
์ ์ฒ๋ฆฌ ์
๋์ด์ฐ๊ธฐ
๊ฐ์ค ๋๋ ์ ๋ต ํ ์คํธ์ ์ผ๋ถ ์ ์ฒ๋ฆฌ ๋จ๊ณ๋ฅผ ์ ์ฉํด์ผ ํ ์ ์์ต๋๋ค. ํ๊ตญ์ด ๋ฌธ์ฅ ๊ตฌ์ฑ์ ๋จ์ด๊ฐ ๋์ด์ฐ๊ธฐ์ ๋ชจํธ์ฑ์ผ๋ก CER๊ณ์ฐ์์ ๊ณต๋ฐฑ์ ๊ณ์ฐํ์ง ์์์ต๋๋ค. ๊ทผ๋ ์ด์ ๊น์ง ๋์์ ์ธ์ด์๋ โ๋์ด์ฐ๊ธฐโ ๊ฐ๋ ์ด ์กด์ฌํ์ง ์์๊ณ , ํ๊ตญ์ด๋ ๋ง์ถค๋ฒ ์ ๋์ด์ฐ๊ธฐ ๊ท์น์ด ์ ํด์ ธ ์๊ธฐ๋ ํ๋, ๋์ด์ฐ๊ธฐ๋ฅผ ์งํค์ง ์์๋ ๋ฌธ์ฅ์ ๋งฅ๋ฝ์ ์ดํดํ๋๋ฐ ํฐ ๋ฌด๋ฆฌ๊ฐ ์๋ ์ธ์ด์ ๋๋ค. ๋ฐ๋ผ์ CER ๊ณ์ฐ์์ ์ ๋ ฅ ๋ณ์์ whitespace๋ ์ ๊ฑฐํฉ๋๋ค. ๊ณต๋ฐฑ ๋ฌธ์๋ \t, \n, \r, \x0b ๋ฐ \x0c์ whitespace์ ๋๋ค.
ref = '๋ ๋ค๋ฅธ ๋ฐฉ๋ฒ์ผ๋ก ๋ฐ์ดํฐ๋ฅผ ์ฝ๋ ์์
๊ณผ ์ฐ๋ ์์
์ ๋ถ๋ฆฌํฉ๋๋ค'
refs -> ๋๋ค๋ฅธ๋ฐฉ๋ฒ์ผ๋ก๋ฐ์ดํฐ๋ฅผ์ฝ๋์์
๊ณผ์ฐ๋์์
์๋ถ๋ฆฌํฉ๋๋ค
๊ตฌ๋์ ์ฒ๋ฆฌ
STT ์ธ์๊ธฐ์ ๋ฐ๋ผ ๊ตฌ๋์ ์ ์ฒ๋ฆฌํ์ง ์๋ ๊ฒฝ์ฐ๊ฐ ๋ง์ต๋๋ค. ์ ๋ ฅ ๋ณ์์ ๊ตฌ๋์ ํํฐ๋ง์ flag์ฒ๋ฆฌ๋ก ์ฌ์ฉํ ์ ์์ต๋๋ค. ํํฐ๋ง ๊ธฐ๋ณธ๊ฐ์ True์ ๋๋ค. ๊ตฌ๋์ ๋ฌธ์๋:
๊ตฌ๋์ filter-> '!"#$%&\'()*+,-./:;<=>?@[\\]^_`{|}~'
import nlptutti as metrics
refs = "๋ ๋ค๋ฅธ ๋ฐฉ๋ฒ์ผ๋ก, ๋ฐ์ดํฐ๋ฅผ ์ฝ๋ ์์
๊ณผ ์ฐ๋ ์์
์ ๋ถ๋ฆฌํฉ๋๋ค!"
preds = "๋! ๋ค๋ฅธ ๋ฐฉ๋ฒ์ผ๋ก ๋ฐ์ดํฐ๋ฅผ ์ฝ๋ ์์
๊ณผ ์ฐ๋ ์์
์ ๋ถ๋ฆฌํฉ๋๋ค."
result = metrics.get_wer(refs, preds, rm_punctuation=True)
# prints: wer -> 0.0
References
-
[1]
. Word Error Rate, https://en.wikipedia.org/wiki/Word_error_rate -
[2]
. Computing error rates, Text Digitisation, https://sites.google.com/site/textdigitisation/qualitymeasures/computingerrorrates