在lintcode刷AI題:貓狗分類器

在lintcode刷AI題:貓狗分類器

來自專欄深度學習搞事情5 人贊了文章

lintcode上面有十幾道類似於Kaggle的小項目,用於深度學習的入手練習再好不過了,現在就讓我們上手這道貓狗分類器的問題吧!

(全程用Keras框架,簡單上手!)

本題網址:LintCode

題目描述:

給出一張貓或狗的圖片,識別出這是貓還是狗。

這種識別具有很重要的意義,比如:

Web服務為了進行保護,會防止一些計算機進行惡意訪問或信息爬取,進而設立一些驗證問題,這些驗證問題對於人來說很容易做,但是對於計算機這很困難。這樣的方法稱為CAPTCHA(完全自動公開的圖靈測試)或HIP(人類交互證明)。 HIP有很多用處,例如減少垃圾郵件,防止暴力破解密碼等。

比較有名的Asirra(用於限制訪問的動物圖像識別)就是一個HIP,它會讓用戶識別圖片信息,比如識別出圖片中是貓還是狗。對於人來說這很容易,但是對於計算機很困難。以下是Asirra的一個例子:

尋找流浪寵物為其提供住所的網站——Petfinder.com,向微軟研究院提供了超過三百萬張貓和狗的圖像,這些圖片由美國各地成千上萬的動物收容所手動分類。

對於要入侵的計算機,隨機猜測一般是最簡單的攻擊方法。圖片識別並不容易,因為圖片之間不同的的背景,角度,姿勢,亮度等都存在著巨大的差異,很難識別。

不過隨著機器學習——尤其是神經網路的發展,這項工作精度可以達到60%以上。而60%分類器就已經能將12幅圖像的猜測概率從1/4096提高到1/459。

這道題目會給大家上萬張的圖片作為訓練集,你能在貓狗之間分辨出它們的差異嗎?

一 下載,探索數據

這道題提供了25000張貓狗圖片,分為訓練集(10000貓,10000狗),測試集(5000張,貓狗未標註)

圖片看起來就像這樣子的:

這裡請使用python將所有圖片都縮放到224*224大小,保存到另一個文件夾中,做完這一步後可以把原始數據刪掉,代碼很簡單,下面是例子:

# 修改圖片大小for i in range(10000): img_path = .貓狗分類器data raincat.%d.jpg%(i) im = Image.open(img_path) resizedIm = im.resize((224, 224)) im.save(r.貓狗分類器data\reshape_traincat.%d.jpg%(i))

二 數據預處理

如果想要用這2W張訓練圖片直接訓練出一個分類器的話,那麼最後的分數並不會很高,原因是圖片實在太少,分類器的泛化能力很差,因此我們為了提升泛化能力(刷分),就需要動用一些訓練好的模型,我們選用的是Keras官方已經訓練好的VGG19網路,提取出VGG19網路最後一層卷積層的輸出數據,每張照片經過模型,轉換為了[7,7,512]大小的數據。

將2W張貓狗圖片全部經過這樣的處理後,保存到一個train_data_x.npy數組裡面去,訓練標籤就設置為一個2w x 1大小的向量,貓用0表示,狗用1表示。同理對於5k張測試集數據,也這樣保存到test_data_x.npy裡面去。

代碼如下:

# 數據預處理# 導入訓練好的VGG網路model = VGG19(weights=imagenet, include_top=False)train_data_x = np.zeros([20000,7,7,512]).astype("float16")train_data_y = np.zeros([20000,])train_data_y[10000:] = 1# 貓的數據0for i in range(10000): img_path = .貓狗分類器data\reshape_traincat.%d.jpg%(i) img = image.load_img(img_path, target_size=(224, 224)) x = image.img_to_array(img) x = np.expand_dims(x, axis=0) x = preprocess_input(x) features = model.predict(x) train_data_x[i, ::] = features print(i)# 狗的數據1for i in range(10000): img_path = .貓狗分類器data\reshape_traindog.%d.jpg%(i) img = image.load_img(img_path, target_size=(224, 224)) x = image.img_to_array(img) x = np.expand_dims(x, axis=0) x = preprocess_input(x) features = model.predict(x) train_data_x[i+10000, ::] = features print(i+10000)np.save("./貓狗分類器data/train_data_x.npy",train_data_x)np.save("./貓狗分類器data/train_data_y.npy",train_data_y)# 測試數據test_data_x = np.zeros([5000,7,7,512]).astype("float16")for i in range(5000): img_path = .貓狗分類器data\reshape_test\%d.jpg%(i) img = image.load_img(img_path, target_size=(224, 224)) x = image.img_to_array(img) x = np.expand_dims(x, axis=0) x = preprocess_input(x) features = model.predict(x) test_data_x[i, ::] = features print(i)np.save("./貓狗分類器data/test_data_x.npy",test_data_x)

初次運行代碼可能需要下載vgg模型,不過此後就再也不需要啦!

三 建立模型,並訓練

在訓練之前先讀取數據,並且將7*7*512的數組平攤成25088長度的向量。

由於在原版的vgg網路中,卷積層後面也都是全連接層,這裡的模型也都使用全連接層。首先將25088->2048->512->64,每一步都是全連接層+dropout+relu,在「64」層後面利用sigmoid轉換成0-1之間的數據,越靠近0,表示預測貓的可能性更大,反之越靠近1,表示預測狗的可能性更大。

在Nvidia GeForce GTX 1050 Ti (4 GB)上,訓練耗時1-2min

# 讀取數據train_data_x = np.load("./貓狗分類器data/train_data_x.npy")train_data_y = np.load("./貓狗分類器data/train_data_y.npy")test_data_x = np.load("./貓狗分類器data/test_data_x.npy")print(train_data_x.shape,train_data_y.shape,test_data_x.shape) # (20000, 7, 7, 512) (20000,) (5000, 7, 7, 512)train_data_x = np.reshape(train_data_x,[train_data_x.shape[0], -1])test_data_x = np.reshape(test_data_x,[test_data_x.shape[0], -1])print(train_data_x.shape,train_data_y.shape,test_data_x.shape) # (20000, 25088) (20000,) (5000, 25088)# 構建模型model = Sequential()model.add(Dense(2048,activation="relu",input_shape=(25088,)))model.add(Dropout(0.5))model.add(Dense(512,activation="relu"))model.add(Dropout(0.5))model.add(Dense(64))model.add(Dense(1,activation="sigmoid"))model.summary()model.compile(loss=binary_crossentropy,optimizer=adadelta,metrics=[accuracy])model.fit(x=train_data_x,y=train_data_y,batch_size=2048,nb_epoch=15,verbose=1)

四 預測,提交數據

這一步就很簡單啦,用訓練好的模型預測貓狗,並寫到submission.csv裡面就行了。

# 預測答案test_y = model.predict_classes(test_data_x)answer = pd.read_csv(open("./貓狗分類器data/sampleSubmission.csv"))answer["label"] = test_yanswer.to_csv("./貓狗分類器data/submission.csv",index=False) # 不要保存引索列

上交後,正確率0.98240,排名5/53

五 開源

所有代碼都在我的github上,下載即運行


推薦閱讀:

還敢吹「毫無PS痕迹」?小心被Adobe官方AI打臉
OpenCV圖像處理|1.20 霍夫線變換
點雲感知 CVPR 2018 論文總結
CVaaS計算機視覺即服務 ——從演算法,應用到服務的技術演變
從VGG到NASNet,一文概覽圖像分類網路

TAG:機器學習 | 深度學習DeepLearning | 計算機視覺 |