【6】基於tensorflow框架微調AlexNet模型以適應不同物體的分類(2)

此處文件包含:標籤製造和讀取,圖像增強

[1]Imageprocess.py

圖像載入 圖像批量處理 數據增強

import tensorflow as tf
import os
import numpy as np
import  cv2

#打開路徑
openpath2='D:\\pythonprocedure\\FineTuningAlexNet\\data\\Lym\\'
#保存路徑
savepath2='D:\\pythonprocedure\\FineTuningAlexNet\\data\\Lymfull\\'

#載入圖片  處理後保存到一個文件夾
def read__image(open_path,save_path):
    nums=0
    images=[]
    for dir_image in os.listdir(open_path): # os.listdir() 方法用於返回指定的文件夾包含的文件或文件夾的名字的列表
        full_path = os.path.abspath(os.path.join(open_path,dir_image))
        if dir_image.endswith('.bmp'):
            image = cv2.imread(full_path)
            image_path = save_path+'%s-%s.jpg' % ('Cell',str(nums))  # 注意這裏圖片名一定要加上擴展名,否則後面imwrite的時候會報錯
            cv2.imwrite(image_path, image)
            nums=nums+1

#載入圖片,處理後保存到一個列表中
def GetImg(open_path):
    patch=[]
    for dir_image in os.listdir(open_path): # os.listdir() 方法用於返回指定的文件夾包含的文件或文件夾的名字的列表
        full_path = os.path.abspath(os.path.join(open_path,dir_image))
        if dir_image.endswith('.jpg'):
            image = cv2.imread(full_path)
            resImg=cv2.resize(image,(227,227))
            patch.append(resImg)
    return  patch

#輸入一張圖片,產生旋轉,縮放,長寬調整等形式
def DateArgutation(images):
    img=images
    imgInfo=img.shape
    height=imgInfo[0]
    width=imgInfo[1]
    agutationimg=[]
    #旋轉3張
    angle=[90,180,280]
    for a in angle:
        matRotate=cv2.getRotationMatrix2D((height*0.5,width*0.5),a,0.5)
        rotateImg=cv2.warpAffine(img,matRotate,(height,width))
        agutationimg.append( rotateImg)

    #縮放3張
    scale=[0.5,2,4]
    for s in scale:
        dstHeight=int(height*s)
        dstWidth=int(width*s)
        resImg=cv2.resize(img,(dstWidth,dstHeight))
        agutationimg.append(resImg)

    #長寬
    change=[[40,50],[60,50],[60,40]]
    for h,w in change:
        reshwImg=cv2.resize(img,(h,w))
        agutationimg.append( reshwImg)


    print('success!')
    return  agutationimg

#打開路徑
openpath1='D:\\pythonprocedure\\FineTuningAlexNet02\\data\\test3\\test\\'
#保存路徑
savepath1='D:\\pythonprocedure\\FineTuningAlexNet02\\data\\test3\\testori\\'
read__image(openpath1,savepath1)

[2]input_selfdata.py

讀取文件夾,製造圖像標籤,然後打亂數據加載到模型中

import tensorflow as tf
import os
import numpy as np
import cv2

#生成訓練圖片的路徑
#train_dir='D:\\pythonprocedure\\FineTuningAlexNet02\\data\\cell'

'''
函數get_files:
載入圖片製造標籤,並打亂(原始圖片爲jpg,bmp格式容易報錯,一般轉成jpg格式)
'''


#獲取圖片,存放到對應的列表中,同時貼上標籤,存放到label列表中
def get_files(file_dir):
    #待分類的細胞
    #淋巴細胞0
    Lyms =[]
    label_Lyms =[]
    #中性細胞1
    Neus =[]
    label_Neus =[]
    #其他細胞
    Others =[]
    label_Others =[]
    for dir_image in os.listdir(file_dir): # os.listdir() 方法用於返回指定的文件夾包含的文件或文件夾的名字的列表
        full_path = os.path.abspath(os.path.join(file_dir,dir_image))
        if dir_image.endswith('.jpg'):
            image = cv2.imread(full_path)
            #分離文件路徑和文件名
            (filepath, filename) = os.path.split(full_path)
            #分離文件名和後綴
            nameall = os.path.splitext(filename)
            #分割文件名,保留第一個字符串的2到5,,原始字符串爲 Lym-1
            name=str(nameall).split('-')[0][2:5]
            #print(name)
            resizeds = cv2.resize(image, (227, 227))
            if name=='Lym':
                Lyms.append(full_path)
                label_Lyms.append(0)
            elif name=='Neu':
                Neus.append(full_path)
                label_Neus.append(1)
            else:
                Others.append(full_path)
                label_Others.append(2)

    #合併數據 圖片和標籤均在水平方向平鋪。
    image_list = np.hstack((Lyms, Neus,Others))
    #print(image_list.shape)
    label_list = np.hstack((label_Lyms, label_Neus,label_Others))
    #print(label_list.shape)
    #利用shuffle打亂數據,先合併爲一個數組在打亂
    temp = np.array([image_list, label_list])
    temp = temp.transpose()  # 轉置
    np.random.shuffle(temp)
    #print(temp.shape)
    #將所有的image和label轉換成list
    #第一列都是img
    image_list = list(temp[:,0])
    #第二列都是label
    label_list = list(temp[:,1])
    label_list = [int(i) for i in label_list]
    #返回兩個list,一個img一個是list
    return image_list, label_list

#將上面生成的List傳入get_batch() ,轉換類型,產生一個輸入隊列queue,因爲img和label
#是分開的,所以使用tf.train.slice_input_producer(),然後用tf.read_file()從隊列中讀取圖像
#數據和標籤:image,label;圖像的尺寸:image_W,image_H,;每一輪填充的圖像;batch_size,;隊列的容量:capacity
def get_batch(image,label,image_W,image_H,batch_size,capacity):

    #將python.list類型轉換成tf能夠識別的格式 tf.cast(x, dtype, name=None) cast爲類型轉換函數
    image=tf.cast(image,tf.string)
    label=tf.cast(label,tf.int32)

    #產生一個輸入隊列queue
    input_queue=tf.train.slice_input_producer([image,label])

    label=input_queue[1]
    image_contents=tf.read_file(input_queue[0])
    #將圖像解碼,不同類型的圖像不能混在一起,要麼只用jpeg,要麼只用png等。
    image=tf.image.decode_jpeg(image_contents,channels=3)

    #將數據預處理,對圖像進行旋轉、縮放、裁剪、歸一化等操作,讓計算出的模型更健壯。
    #裁剪或將圖像填充到目標寬度和高度.
    image=tf.image.resize_image_with_crop_or_pad(image,image_W,image_H)
    #圖像歸一化
    image=tf.image.per_image_standardization(image)

    #生成batch ;num_threads 線程數,使用多少個線程來控制整個隊列
    image_batch,label_batch=tf.train.batch([image,label],batch_size=batch_size,num_threads=64,capacity=capacity)

    #重新排列標籤,行數爲[batch_size]
    #label_batch=tf.reshape(label_batch,[batch_size]) 數據類型轉換
    image_batch=tf.cast(image_batch,tf.float32)

    return image_batch,label_batch




# #顯示標籤
# (image_list, label_list)=get_files(train_dir)
# length=len(image_list)
# for index in range(length):
#     path=image_list[index]
#     img=cv2.imread(path)
#     text1='圖像和標籤顯示:'+str(index)
#     #print(text1)
#     text='Label:'+str(label_list[index])
#     img_resizeds = cv2.resize(img, (700, 500))
#     cv2.putText(img_resizeds,text, (20,20), cv2.FONT_HERSHEY_SIMPLEX, 1, (0, 255, 0), 2)
#     cv2.imshow('label_image',img_resizeds)
#     cv2.waitKey(1000)

TFRecord格式的標籤製造與讀取,項目中採用的不是此類的

[3]Labeledimage_TFRecord.py

製造tfrecord格式的標籤

# -*- coding: utf-8 -*-
import os
import tensorflow as tf
from PIL import Image
import matplotlib.pyplot as plt
import numpy as np
import cv2

#cwd='./data/train/'
#cwd='./data/test/'
file_dir='D:\\pythonprocedure\\FineTuningAlexNet\\data\\cell'
classes={'Lym','Neu'}  #人爲設定2類
#writer= tf.python_io.TFRecordWriter("dog_and_cat_train.tfrecords") #要生成的文件
writer= tf.python_io.TFRecordWriter("LNtest.tfrecords") #要生成的文件

for dir_image in os.listdir(file_dir): # os.listdir() 方法用於返回指定的文件夾包含的文件或文件夾的名字的列表
    full_path = os.path.abspath(os.path.join(file_dir,dir_image))
    if dir_image.endswith('.bmp'):
        image = cv2.imread(full_path)
        #分離文件路徑和文件名
        (filepath, filename) = os.path.split(full_path)
        #分離文件名和後綴
        nameall = os.path.splitext(filename)
        #分割文件名,保留第一個字符串的2到5,,原始字符串爲 Lym-1
        name=str(nameall).split('-')[0][2:5]
        #print(name)
        resizeds = cv2.resize(image, (227, 227))
        img_raw=resizeds.tobytes()
        if name=='Lym':
             example = tf.train.Example(features=tf.train.Features(feature={
            "label": tf.train.Feature(int64_list=tf.train.Int64List(value=[0])),
            'img_raw': tf.train.Feature(bytes_list=tf.train.BytesList(value=[ img_raw]))
        })) #example對象對label和image數據進行封裝
        else:
            example = tf.train.Example(features=tf.train.Features(feature={
            "label": tf.train.Feature(int64_list=tf.train.Int64List(value=[1])),
            'img_raw': tf.train.Feature(bytes_list=tf.train.BytesList(value=[ img_raw]))
        })) #example對象對label和image數據進行封裝
        writer.write(example.SerializeToString())  #序列化爲字符串
writer.close()



[4]ReadMyOwnData.py

載入tfrecord格式的標籤

#!/usr/bin/env python2
# -*- coding: utf-8 -*-

import numpy as np
import tensorflow as tf
import cv2

def read_and_decode(filename): # 讀入tfrecords
    filename_queue = tf.train.string_input_producer([filename],shuffle=True)#生成一個queue隊列

    reader = tf.TFRecordReader()
    _, serialized_example = reader.read(filename_queue)#返回文件名和文件
    features = tf.parse_single_example(serialized_example,
                                       features={
                                           'label': tf.FixedLenFeature([], tf.int64),
                                           'img_raw' : tf.FixedLenFeature([], tf.string),
                                       })#將image數據和label取出來

    img = tf.decode_raw(features['img_raw'], tf.uint8)
    img = tf.reshape(img, [128, 128, 3])  #reshape爲128*128的3通道圖片
    img = tf.cast(img, tf.float32) * (1. / 255) - 0.5 #在流中拋出img張量
    label = tf.cast(features['label'], tf.int32) #在流中拋出label張量

    return img, label

img, label=read_and_decode("LNtest.tfrecords")
#print(label)

【5】Ckpt_to_npy.py

Ckpt格式轉換爲npy格式的

#coding=gbk
import numpy as np
import tensorflow as tf
from tensorflow.python import pywrap_tensorflow


# open_ckpt_path='D:\\pythonprocedure\\FineTuningAlexNet02\\model\\alexnet_model.ckpt'#your ckpt path
# save_npy_path="D:\\pythonprocedure\\FineTuningAlexNet02\\npydata\\"

"""
mean:此函數是用來將ckpt文件保存爲npy,僅針對AlexNet模型,若爲他用需更改字典
open_ckpt_path:ckpt文件打開路徑
save_npy_path:npy文件保存路徑
"""

def ckpttonpy(open_ckpt_path,save_npy_path):
    reader=pywrap_tensorflow.NewCheckpointReader(open_ckpt_path)
    var_to_shape_map=reader.get_variable_to_shape_map()
    alexnet={}
    alexnet_layer = ['conv1','conv2','conv3','conv4','conv5','fc6','fc7','fc8']
    add_info = ['weights','biases']
    alexnet={'conv1':[[],[]],'conv2':[[],[]],'conv3':[[],[]],'conv4':[[],[]],'conv5':[[],[]],'fc6':[[],[]],'fc7':[[],[]],'fc8':[[],[]]}
    for key in var_to_shape_map:
        #print ("tensor_name",key)
        str_name = key
        # 因爲模型使用Adam算法優化的,在生成的ckpt中,有Adam後綴的tensor
        if str_name.find('Adam') > -1:
            continue
        #print('tensor_name:' , str_name)
        if str_name.find('/') > -1:
            names = str_name.split('/')
            # first layer name and weight, bias
            layer_name = names[0]
            layer_add_info = names[1]
        else:
            layer_name = str_name
            layer_add_info = None

        if layer_add_info == 'weights':
            alexnet[layer_name][0]=reader.get_tensor(key)
        elif layer_add_info == 'biases':
            alexnet[layer_name][1] = reader.get_tensor(key)
        else:
            alexnet[layer_name] = reader.get_tensor(key)
    np.save(save_npy_path+'alexnet_cell.npy',alexnet)
    print("save success!")

 

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章