https://chtseng.wordpress.com/2018/09/01/%E5%BB%BA%E7%AB%8B%E8%87%AA%E5%B7%B1%E7%9A%84yolo%E8%BE%A8%E8%AD%98%E6%A8%A1%E5%9E%8B-%E4%BB%A5%E6%9F%91%E6%A9%98%E8%BE%A8%E8%AD%98%E7%82%BA%E4%BE%8B/
弯弯的,应该进不去
按照这个教程 https://blog.csdn.net/qq_21578849/article/details/84980298
#这是将VOC数据集里面的数据提取一类,我的是person,需要改动的,就是文件夹的名称和位置,以及保存路径
import os
import os.path
import shutil
fileDir_ann = "E:\\VOCdevkit\\VOC2007\\Annotations"
fileDir_img = "E:\\VOCdevkit\\VOC2007\\JPEGImages\\"
saveDir_img = "E:\\VOCdevkit\\VOC2007\\JPEGImages_ssd\\"
if not os.path.exists(saveDir_img):
os.mkdir(saveDir_img)
names = locals()
for files in os.walk(fileDir_ann):
for file in files[2]:
print (file + "-->start!" )
saveDir_ann = "E:\\VOCdevkit\\VOC2007\\Annotations_ssd\\"
if not os.path.exists(saveDir_ann):
os.mkdir(saveDir_ann)
fp = open(fileDir_ann + '\\' + file)
saveDir_ann = saveDir_ann + file
fp_w = open(saveDir_ann, 'w')
classes = ['aeroplane','bicycle','bird','boat','bottle','bus','car','cat','chair','cow','diningtable','dog','horse','motorbike','pottedplant','sheep','sofa','train','tvmonitor','person']
lines = fp.readlines()
ind_start = []
ind_end = []
lines_id_start = lines[:]
lines_id_end = lines[:]
classes1 = '\t\tperson \n'
#classes2 = '\t\tmotorbike \n'
#classes3 = '\t\tbus \n'
#classes4 = '\t\tcar \n'
while "\t\n")
ind_end.append(b)
lines_id_end[b] = "delete"
i = 0
for k in range(0,len(ind_start)):
names['block%d'%k] = []
for j in range(0,len(classes)):
if classes[j] in lines[ind_start[i]+1]:
a = ind_start[i]
for o in range(ind_end[i]-ind_start[i]+1):
names['block%d'%k].append(lines[a+o])
break
i += 1
string_start = lines[0:ind_start[0]]
a = 0
for k in range(0,len(ind_start)):
if classes1 in names['block%d'%k]:
a += 1
string_start += names['block%d'%k]
#if classes2 in names['block%d'%k]:
a += 1
string_start += names['block%d'%k]
#if classes3 in names['block%d'%k]:
a += 1
string_start += names['block%d'%k]
string_start += lines[ind_end[-1]+1:]
for c in range(0,len(string_start)):
fp_w.write(string_start[c])
fp_w.close()
if a == 0:
os.remove(saveDir_ann)
else:
name_img = fileDir_img + os.path.splitext(file)[0] + ".jpg"
shutil.copy(name_img,saveDir_img)
fp.close()
混合完数据之后,钥生成yolo的txt格式。将下面的要生成到同一级的目录下面
比如:
import os
import random
trainval_percent = 0.1
train_percent = 0.9
xmlfilepath = 'Annotations'
txtsavepath = 'ImageSets\Main'
total_xml = os.listdir(xmlfilepath)
num = len(total_xml)
list = range(num)
tv = int(num * trainval_percent)
tr = int(tv * train_percent)
trainval = random.sample(list, tv)
train = random.sample(trainval, tr)
ftrainval = open('ImageSets/Main/trainval.txt', 'w')
ftest = open('ImageSets/Main/test.txt', 'w')
ftrain = open('ImageSets/Main/train.txt', 'w')
fval = open('ImageSets/Main/val.txt', 'w')
for i in list:
name = total_xml[i][:-4] + '\n'
if i in trainval:
ftrainval.write(name)
if i in train:
ftest.write(name)
else:
fval.write(name)
else:
ftrain.write(name)
ftrainval.close()
ftrain.close()
fval.close()
ftest.close()
之后跟着上面的链接教程一步一步的做就可以了
训练过程结束后,没有问题,测试的时候按照别人的指令发现有这样的错误
Loading weights from yolov3.weights...Done!
data/dog.jpg: Predicted in 0.423082 seconds.
段错误 (核心已转储)
目前暂时不知道要怎么修改,而且连用之前的yolo训练都没有用。
https://blog.csdn.net/NcepuKZH/article/details/88805269
依据这篇博客也不知道有没有用
上面的对我没用!
错误信息
names: Using default 'data/names.list'
Couldn't open file: data/names.list
解决方法:指令输入错误
./darknet detector test cfg/voc.data cfg/yolov3-voc.cfg backup/yolov3-voc_900.weights
要将自己的.data放在前面
剩下的就是自己代码的问题‘,什么问题呢?就是之前的源代码用的是yolov2的版本,但是我训练的模型是yolov3,导致python的接口无法调用相应的函数,于是抱着尝试的心态,找到相关博客修改源码。
出现的错误应该是不存在mudoles的之类的错误,也就是我上面说的版本的问题,于是改为了yolo3可以用的。不说废话以下开始
这里是将image.c文件里面要加上这一行,应该是为了处理2那边的图片array_to_image
#ifdef NUMPY
image ndarray_to_image(unsigned char* src, long* shape, long* strides)
{
int h = shape[0];
int w = shape[1];
int c = shape[2];
int step_h = strides[0];
int step_w = strides[1];
int step_c = strides[2];
image im = make_image(w, h, c);
int i, j, k;
int index1, index2 = 0;
for(i = 0; i < h; ++i){
for(k= 0; k < c; ++k){
for(j = 0; j < w; ++j){
index1 = k*w*h + i*w + j;
index2 = step_h*i + step_w*j + step_c*k;
//fprintf(stderr, "w=%d h=%d c=%d step_w=%d step_h=%d step_c=%d \n", w, h, c, step_w, step_h, step_c);
//fprintf(stderr, "im.data[%d]=%u data[%d]=%f \n", index1, src[index2], index2, src[index2]/255.);
im.data[index1] = src[index2]/255.;
}
}
}
rgbgr_image(im);
return im;
}
#endif
相应的image.h要加上
#ifdef NUMPY
image ndarray_to_image(unsigned char* src, long* shape, long* strides);
#endif
同时makefile文件中要加上
ifeq ($(NUMPY), 1)
COMMON+= -DNUMPY -I/usr/include/python2.7/ -I/usr/lib/python2.7/dist-packages/numpy/core/include/numpy/
CFLAGS+= -DNUMPY
endif
并且第一行
GPU=1
CUDNN=1
OPENCV=1
OPENMP=0
NUMPY=1
DEBUG=0
接着就可以make clean +make了
不出意外是不会出错的
接下来就要在darknet.py中定义相关需要调用的函数了
将图片的格式改掉,line 136
def nparray_to_image(img):
data = img.ctypes.data_as(POINTER(c_ubyte))
image = ndarray_image(data, img.ctypes.shape, img.ctypes.strides)
return image
ndarray_image = lib.ndarray_to_image
ndarray_image.argtypes = [POINTER(c_ubyte), POINTER(c_long), POINTER(c_long)]
ndarray_image.restype = IMAGE
上面的位置大概是在116 lines左右
还有就是line 145
def detect(net, meta, im, thresh=.5, hier_thresh=.5, nms=.45):
#im = load_image(image, 0, 0)
最后就是主函数,我认为可改可不改,保险起见我还是改了,改为自己的,不如最后应该是看自己代码调用了什么权重的函数决定的
if __name__ == "__main__":
#net = load_net("cfg/densenet201.cfg", "/home/pjreddie/trained/densenet201.weights", 0)
#im = load_image("data/wolf.jpg", 0, 0)
#meta = load_meta("cfg/imagenet1k.data")
#r = classify(net, meta, im)
#print r[:10]
net = load_net("cfg/yolov3-voc.cfg", "backup/yolov3-voc_2100.weights", 0)
meta = load_meta("cfg/voc.data")
r = detect(net, meta, img)
print (r)#to change python3 to python2
参考博客的链接:
https://blog.csdn.net/weixin_43202256/article/details/83009393( 博客中有些许的错误已经改正)
https://github.com/pjreddie/darknet/issues/289 (此乃真大神,代码看这个很稳妥)
至此,所有的代码就跑通了。优化的问题就是后面的事情了。
另外就是yolo测试的时候一定不要吝啬开自己的gpu啊!!!950的显卡,原本以为我的显卡很渣就没有调用GPU,但是试过之后速度从12fps变为了0.2s????大吃一惊!