仅供参考,目前实现的格式转化还是存在一定的问题,导致训练后的模型精度很高,分配上还是没有完全符合market1501的格式。依照这样训练的模型,效果还可以,
git clone https://github.com/KaiyangZhou/deep-person-reid.git
目录介绍
1) “bounding_box_test”——用于测试集的 750 人,包含 19,732 张图像,前缀为 0000 表示在提取这 750 人的过程中DPM检测错的图(可能与query是同一个人),-1 表示检测出来其他人的图(不在这 750 人中)
2) “bounding_box_train”——用于训练集的 751 人,包含 12,936 张图像
3) “query”——为 750 人在每个摄像头中随机选择一张图像作为query,因此一个人的query最多有 6 个,共有 3,368 张图像
4) “gt_query”——matlab格式,用于判断一个query的哪些图片是好的匹配(同一个人不同摄像头的图像)和不好的匹配(同一个人同一个摄像头的图像或非同一个人的图像)
5) “gt_bbox”——手工标注的bounding box,用于判断DPM检测的bounding box是不是一个好的box
命名规则
以 0001_c1s1_000151_01.jpg 为例
1) 0001 表示每个人的标签编号,从0001到1501;
2) c1 表示第一个摄像头(camera1),共有6个摄像头;
3) s1 表示第一个录像片段(sequece1),每个摄像机都有数个录像段;
4) 000151 表示 c1s1 的第000151帧图片,视频帧率25fps;
5) 01 表示 c1s1_001051 这一帧上的第1个检测框,由于采用DPM检测器,对于每一帧上的行人可能会框出好几个bbox。00 表示手工标注框
import os
import shutil
import random
# 输入数据文件夹
input_pedestrian_folder = r"F:\sjh\code\deep-person-reid\reid-data\my_data\person"
input_vehicle_folder = r"F:\sjh\code\deep-person-reid\reid-data\my_data\car"
# 输出数据文件夹
output_root = r"F:\sjh\code\deep-person-reid\reid-data\my_data/Market1501"
bounding_box_train = os.path.join(output_root, "bounding_box_train")
bounding_box_test = os.path.join(output_root, "bounding_box_test")
query = os.path.join(output_root, "query")
if os.path.exists(bounding_box_train):
shutil.rmtree(bounding_box_train)
shutil.rmtree(bounding_box_test)
shutil.rmtree(query)
os.makedirs(bounding_box_train, exist_ok=True)
os.makedirs(bounding_box_test, exist_ok=True)
os.makedirs(query, exist_ok=True)
def rename_and_split_images(input_folder, pid_start, camid, query_bool=False,classes=0):
pid = pid_start
image_files = os.listdir(input_folder)
frame = 1
for image_file in image_files:
# 为每个行人/车辆分配一个唯一的pid
# pid += 1
# if classes == 1:
# pid = 1
# elif classes == 2:
# pid = 2
src_path = os.path.join(input_folder, image_file)
# 在这里,我们假设每个输入文件夹只有一个摄像头和连续的帧
frame += 1
new_image_name = f"{pid:04d}_c{camid}s{camid}_{frame:06d}.jpg"
dest_path = os.path.join(bounding_box_train, new_image_name)
shutil.copyfile(src_path, dest_path)
# 随机选择一些图像分配给bounding_box_test和query
if random.random() < 0.1:
frame += 1
new_image_name = f"{pid:04d}_c{camid}s{camid}_{frame:06d}.jpg"
dest_path = os.path.join(bounding_box_test, new_image_name)
shutil.copyfile(src_path, dest_path)
frame += 1
if query_bool:
camid=2
new_image_name = f"{pid:04d}_c{camid}s{camid}_{frame:06d}.jpg"
dest_path = os.path.join(query, new_image_name)
shutil.copyfile(src_path, dest_path)
return pid
# 处理行人数据
last_pid = rename_and_split_images(input_pedestrian_folder, 0, 1,query_bool=True,classes=1)
# 处理车辆数据
rename_and_split_images(input_vehicle_folder, 1, 2, query_bool=True,classes=2)
数据存放位置,最后会生成market1501,用于训练的三个文件train、test、query:
代码命名规则:
0000_c1s1_000002.jpg
新建一个train.py文件
import torchreid
if __name__ == '__main__':
datamanager = torchreid.data.ImageDataManager(
root="reid-data",#/market1501
sources="market1501",
targets="market1501",
height=256,
width=128,
batch_size_train=36,
batch_size_test=1,
transforms=["random_flip", "random_crop"]
)
model = torchreid.models.build_model(
name="resnet50",
num_classes=datamanager.num_train_pids,
loss="softmax",
pretrained=True
)
model = model.cuda()
optimizer = torchreid.optim.build_optimizer(
model,
optim="adam",
lr=0.0003
)
scheduler = torchreid.optim.build_lr_scheduler(
optimizer,
lr_scheduler="single_step",
stepsize=20
)
engine = torchreid.engine.ImageSoftmaxEngine(
datamanager,
model,
optimizer=optimizer,
scheduler=scheduler,
label_smooth=True
)
engine.run(
save_dir="log/resnet50",
max_epoch=20,
eval_freq=1,
print_freq=1,
test_only=False
)
parser.add_argument('--yolo-weights', nargs='+', type=Path, default=WEIGHTS / 'yolov5s.pt', help='model.pt path(s)')
parser.add_argument('--reid-weights', type=Path, default=WEIGHTS / 'resnet50_market1501.pt')
parser.add_argument('--tracking-method', type=str, default='bytetrack', help='strongsort, ocsort, bytetrack')#bytetrack最快,效果也比较好