opencv - How to implement .dat file for handwritten recognition using SVM in Python -
i've been trying train hand-written digits using svm based on code on opencv library. training part follow:
import cv2 import numpy np sz=20 bin_n = 16 svm_params = dict( kernel_type = cv2.svm_linear, svm_type = cv2.svm_c_svc, c=2.67, gamma=5.383 ) affine_flags = cv2.warp_inverse_map|cv2.inter_linear def deskew(img): m = cv2.moments(img) if abs(m['mu02']) < 1e-2: return img.copy() skew = m['mu11']/m['mu02'] m = np.float32([[1, skew, -0.5*sz*skew], [0, 1, 0]]) img = cv2.warpaffine(img,m,(sz, sz),flags=affine_flags) return img def hog(img): gx = cv2.sobel(img, cv2.cv_32f, 1, 0) gy = cv2.sobel(img, cv2.cv_32f, 0, 1) mag, ang = cv2.carttopolar(gx, gy) bins = np.int32(bin_n*ang/(2*np.pi)) # quantizing binvalues in (0...16) bin_cells = bins[:10,:10], bins[10:,:10], bins[:10,10:], bins[10:,10:] mag_cells = mag[:10,:10], mag[10:,:10], mag[:10,10:], mag[10:,10:] hists = [np.bincount(b.ravel(), m.ravel(), bin_n) b, m in zip(bin_cells, mag_cells)] hist = np.hstack(hists) # hist 64 bit vector return hist img = cv2.imread('digits.png',0) if img none: raise exception("we need digits.png image samples/data here !") cells = [np.hsplit(row,100) row in np.vsplit(img,50)] train_cells = [ i[:50] in cells ] test_cells = [ i[50:] in cells] deskewed = [map(deskew,row) row in train_cells] hogdata = [map(hog,row) row in deskewed] traindata = np.float32(hogdata).reshape(-1,64) responses = np.float32(np.repeat(np.arange(10),250)[:,np.newaxis]) svm = cv2.svm() svm.train(traindata,responses, params=svm_params) svm.save('svm_data.dat')
heres digits.png enter image description here
as result, got svm_data.dat file. don't know how implement model. lets want read number here enter image description here
can me out please?
i going assume "how implement model" mean "how predict label new image".
first off, note not have saved svm_data.dat
per se, unless want in different script/session, in case can reload trained svm
object file.
with out of way, making prediction new data requires 3 steps:
if new data somehow different training data, preprocess matches training data (see inverting , resizing below).
extract features same way done training data.
use trained classifier predict label.
for example image uploaded, can done follows:
# load image img_predict = cv2.imread('predict.png', 0) # preprocessing: image inverted compared training data # here inverted img_predict = np.invert(img_predict) # preprocessing: has different size # resizes same size training data img_predict = cv2.resize(img_predict, (20, 20), interpolation=cv2.inter_cubic) # extract features img_predict_ready = np.float32(hog(deskew(img_predict))) # reload trained svm # not necessary if predicting done in same session training svm = cv2.svm() svm.load("svm_data.dat") # run prediction prediction = svm.predict(img_predict_ready) print int(prediction)
the output 0
, expected.
note important match data want classify data used training. in case, skipping re-sizing step lead mis-classification of image 2
.
furthermore, closer @ image reveals still bit different training data (more background, different mean), not surprised if classifier ends performing bit worse on images compared test data used in original tutorial (which half of training data). however, depends on how sensitive feature extraction differences between training images , prediction images.
wiki
Comments
Post a Comment