자연어 처리를 학습하면서 word2vec 기법을 많이 사용하였는데 현재 백앤드를 구현하는 분이 mysql로 구현하여 별도로 다른 데이터 베이스를 구현하거나 같이 사용하는 것을 고민하였는데 같이 mysql에 저장하는 걸로 결정하였다.
하지만 처음에는 무난하게 진행하던 중 엄청 큰 벡터값을 저장하는데 문제가 발생하였고 해당 내용을 정리하고자 작성하였다.
우선적으로 Python 에서 mysqldb를 사용하게 되면 해당 컬럼이 string 형이면 string으로 바뀌어서 들어가게 된다.
처음에는 벡터값을 db에 저장하고 꺼내서 유사도를 측정하는데 차원수가 자꾸 틀려서 이해를 하지 못했는데 벡터값이 float64 인지 float32인지를 보고 변환을 해야한다.
자신의 벡터값이 float64 인지 float32 인지 알고 변환하기
처음에 했던 실수가 mysql 자료형을 varchar(255)로 되어있는 줄 모르고 차원이 자꾸 짤려서 string -> vector로 바꾸는데 에러가 발생한다고 생각하여 string -> Bytes -> vector 형식으로 변경하려고 하였다.
참고 : https://stackoverflow.com/questions/6485790/numpy-array-to-base64-and-back-to-numpy-array-python
import base64
import numpy as np
t = np.arange(25, dtype=np.float64)
s = base64.b64encode(t)
r = base64.decodebytes(s)
q = np.frombuffer(r, dtype=np.float64)
print(np.allclose(q, t))
위의 자료를 보고 바이트 코드로 인코딩하고 디코딩하여 사용하려고 했는데 차원수가 dim10 != dim5 오류가 발생하여 어떤 오류인지 다시 확인하였다.
직접 들어갔을떄랑 나왔을떄를 비교하였는데 mysql 에서 binary 자료형이 최대가 255이기 때문에 차원이 높아서 뒷부분이 짤렸던 것이다.
따라서 다시 byte-> vector 에서 string-> vector 방법을 찾아 보았다.
import numpy as np
s = '[0 1 2 3]'
a = np.fromstring(s[1:-1], dtype=np.int, sep=' ')
print(a) # [0 1 2 3]
위의 코드를 보는 것처럼 '[]' vector 값을 string으로 저장을 하는 동시에 꺼내서 사용할 때 fromstring을 사용하여 해결하면 된다.
그리고 앞에서 말했던 것처럼 dtype 타입에서 자신의 벡터값이 float64, float32인지 넣어서 유사도를 측정하면 해결 할 수 있을 것이다.