Skip to content

Commit 486ab8c

Browse files
committed
minor changes
1 parent 35bc75a commit 486ab8c

File tree

4 files changed

+95
-73
lines changed

4 files changed

+95
-73
lines changed

models_detection/KerasYOLO.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -49,7 +49,7 @@ class KerasYOLO:
4949
COORD_SCALE = 1.0
5050
CLASS_SCALE = 1.0
5151

52-
BATCH_SIZE = 1
52+
BATCH_SIZE = 32
5353
WARM_UP_BATCHES = 0
5454
TRUE_BOX_BUFFER = 50
5555

models_tracking/MultiObjDetTracker.py

Lines changed: 29 additions & 14 deletions
Original file line numberDiff line numberDiff line change
@@ -12,7 +12,7 @@
1212
from keras.models import Sequential, Model
1313
from keras.layers import Reshape, Activation, Conv2D, Input, MaxPooling2D, BatchNormalization, Flatten, Dense, Lambda, ConvLSTM2D
1414
from keras.layers.advanced_activations import LeakyReLU
15-
from keras.callbacks import EarlyStopping, ModelCheckpoint, TensorBoard
15+
from keras.callbacks import EarlyStopping, ModelCheckpoint, TensorBoard, ReduceLROnPlateau
1616
from keras.optimizers import SGD, Adam, RMSprop
1717
from keras.layers.wrappers import TimeDistributed
1818
from keras.layers.merge import concatenate
@@ -80,8 +80,8 @@ class MultiObjDetTracker:
8080
]
8181

8282
LABELS = LABELS_MOT17
83-
IMAGE_H, IMAGE_W = 608, 608 # 416
84-
GRID_H, GRID_W = 19 , 19 # 13
83+
IMAGE_H, IMAGE_W = 416, 416 # 416
84+
GRID_H, GRID_W = 13 , 13 # 13
8585
BOX = 5
8686
CLASS = len(LABELS)
8787
CLASS_WEIGHTS = np.ones(CLASS, dtype='float32')
@@ -101,6 +101,10 @@ class MultiObjDetTracker:
101101
SEQUENCE_LENGTH = 4
102102
MAX_BOX_PER_IMAGE = 50
103103

104+
LOAD_MODEL = True
105+
INITIAL_EPOCH = 0
106+
SAVED_MODEL_PATH = 'models/MultiObjDetTracker-CHKPNT-03-0.55.hdf5'
107+
104108
# train_image_folder = 'data/ImageNet-ObjectDetection/ILSVRC2015Train/Data/VID/train/'
105109
# train_annot_folder = 'data/ImageNet-ObjectDetection/ILSVRC2015Train/Annotations/VID/train/'
106110
# valid_image_folder = 'data/ImageNet-ObjectDetection/ILSVRC2015Train/Data/VID/val/'
@@ -117,14 +121,16 @@ class MultiObjDetTracker:
117121

118122
def __init__(self, argv={}):
119123
argv['LABELS'] = self.LABELS
120-
argv['BATCH_SIZE'] = self.BATCH_SIZE
124+
argv['BATCH_SIZE'] = self.BATCH_SIZE * self.SEQUENCE_LENGTH
121125
argv['IMAGE_H'] = self.IMAGE_H
122126
argv['IMAGE_W'] = self.IMAGE_W
123127
argv['GRID_H'] = self.GRID_H
124128
argv['GRID_W'] = self.GRID_W
125129

126130
self.detector = KerasYOLO(argv)
127131
self.load_model()
132+
if self.LOAD_MODEL:
133+
self.load_weights()
128134

129135
def loss_fxn(self, y_true, y_pred, tboxes, message=''):
130136
return self.detector.loss_fxn(y_true, y_pred, tboxes, message=message)
@@ -167,7 +173,7 @@ def load_model(self):
167173
output_det = TimeDistributed(Reshape((self.GRID_H, self.GRID_W, self.BOX, 4 + 1 + self.CLASS)), name='detection')(x_bbox)
168174

169175
z = concatenate([x_bbox, x_vis])
170-
z_vis = ConvLSTM2D(1024, (3,3), strides=(1,1), padding='same', return_sequences=True, name='tconv_lstm')(z)
176+
z_vis = ConvLSTM2D(512, (3,3), strides=(1,1), padding='same', return_sequences=True, name='tconv_lstm')(z)
171177

172178
# z = TimeDistributed(Conv2D(1024, (3,3), strides=(1,1), padding='same', use_bias=False, name='tconv_1'), name='timedist_tconv1')(z)
173179
# z = TimeDistributed(BatchNormalization(name='tnorm_1'), name='timedist_tnorm')(z)
@@ -207,7 +213,7 @@ def load_data_generators(self, generator_config):
207213
pickle.dump(valid_imgs, fp)
208214

209215

210-
train_batch = BatchSequenceGenerator1(train_imgs, generator_config, norm=normalize, shuffle=True, augment=False)
216+
train_batch = BatchSequenceGenerator1(train_imgs, generator_config, norm=normalize, shuffle=True, augment=True)
211217
valid_batch = BatchSequenceGenerator1(valid_imgs, generator_config, norm=normalize, augment=False)
212218

213219
return train_batch, valid_batch
@@ -244,38 +250,47 @@ def train(self):
244250
mode = 'min',
245251
verbose = 1)
246252

247-
checkpoint = ModelCheckpoint('weights/WEIGHTS_MultiObjDetTracker.h5',
253+
checkpoint = ModelCheckpoint('models/MultiObjDetTracker-CHKPNT-{epoch:02d}-{val_loss:.2f}.hdf5',
248254
monitor = 'val_loss',
249255
verbose = 1,
250-
save_best_only = True,
256+
save_best_only = False,
251257
# save_weights_only = True,
252258
mode = 'min',
253259
period = 1)
254260

261+
reduce_lr = ReduceLROnPlateau(monitor = 'val_loss',
262+
factor = 0.5,
263+
patience = 2,
264+
verbose = 1,
265+
mode = 'auto',
266+
min_lr = 1e-5)
267+
255268
tb_counter = len([log for log in os.listdir(os.path.expanduser('./logs/')) if 'MultiObjDetTracker_' in log]) + 1
256269
tensorboard = TensorBoard(log_dir = os.path.expanduser('./logs/') + 'MultiObjDetTracker_' + str(tb_counter),
257270
histogram_freq = 0,
258271
write_graph = True,
259272
write_images = False)
260273

261-
optimizer = Adam(lr=1e-5, beta_1=0.9, beta_2=0.999, epsilon=1e-08, decay=0.0)
274+
optimizer = Adam(lr=1e-4, beta_1=0.9, beta_2=0.999, epsilon=1e-08, decay=0.0)
262275
#optimizer = SGD(lr=1e-4, decay=0.0005, momentum=0.9)
263276
#optimizer = RMSprop(lr=1e-4, rho=0.9, epsilon=1e-08, decay=0.0)
264277

265-
self.model.compile(loss=[self.custom_loss_ttrack, self.custom_loss_dtrack], loss_weights=[1.5, 1.0], optimizer=optimizer)
278+
self.model.compile(loss=[self.custom_loss_ttrack, self.custom_loss_dtrack], loss_weights=[0.7, 0.3], optimizer=optimizer)
266279
self.model.fit_generator(
267280
generator = train_batch,
268281
steps_per_epoch = len(train_batch),
269282
epochs = 100,
270283
verbose = 1,
271284
validation_data = valid_batch,
272285
validation_steps = len(valid_batch),
273-
callbacks = [early_stop, checkpoint, tensorboard],
274-
max_queue_size = 3)
286+
callbacks = [early_stop, checkpoint, tensorboard, reduce_lr],
287+
max_queue_size = 3,
288+
initial_epoch = self.INITIAL_EPOCH)
275289

276290

277-
def load_weights(self, weight_path):
278-
self.model.load_weights(weight_path)
291+
def load_weights(self):
292+
self.model.load_weights(self.SAVED_MODEL_PATH)
293+
self.INITIAL_EPOCH = int(self.SAVED_MODEL_PATH.split('-')[2])
279294

280295
def predict(self, input_paths, output_paths):
281296
assert len(input_paths)==self.SEQUENCE_LENGTH

utility/motd_to_pascal.py

Lines changed: 58 additions & 51 deletions
Original file line numberDiff line numberDiff line change
@@ -59,60 +59,67 @@ def instance_to_xml(obj):
5959

6060
def create_annotations(validation_split):
6161
anns = []
62-
ann_dir = 'data/MOT17/MOT17DetLabels/train/'
63-
for (dirpath, dirnames, filenames) in os.walk(ann_dir):
64-
if len(filenames)==0:
65-
continue
66-
for filename in sorted(filenames):
67-
if filename.endswith('.ini')==True:
68-
ann = {}
69-
seq_info = dirpath + '/' + filename
70-
with open(seq_info) as f:
71-
lines = f.readlines()
72-
ann['folder'] = lines[1].rstrip('\n').split('=')[-1]
73-
ann['imdir'] = lines[2].rstrip('\n').split('=')[-1]
74-
ann['length'] = lines[4].rstrip('\n').split('=')[-1]
75-
ann['width'] = lines[5].rstrip('\n').split('=')[-1]
76-
ann['height'] = lines[6].rstrip('\n').split('=')[-1]
77-
ann['imext'] = lines[7].rstrip('\n').split('=')[-1]
78-
anns.append(ann)
62+
ann_dirs = ['data/MOT17/MOT17DetLabels/train/', 'data/MOT17/MOT17DetLabels/test/']
63+
for ann_dir in ann_dirs:
64+
for (dirpath, dirnames, filenames) in os.walk(ann_dir):
65+
if len(filenames)==0:
66+
continue
67+
for filename in sorted(filenames):
68+
if filename.endswith('.ini')==True:
69+
ann = {}
70+
seq_info = dirpath + '/' + filename
71+
with open(seq_info) as f:
72+
lines = f.readlines()
73+
ann['folder'] = lines[1].rstrip('\n').split('=')[-1]
74+
ann['imdir'] = lines[2].rstrip('\n').split('=')[-1]
75+
ann['length'] = lines[4].rstrip('\n').split('=')[-1]
76+
ann['width'] = lines[5].rstrip('\n').split('=')[-1]
77+
ann['height'] = lines[6].rstrip('\n').split('=')[-1]
78+
ann['imext'] = lines[7].rstrip('\n').split('=')[-1]
79+
anns.append(ann)
7980

80-
for ann in anns:
81-
xml_data = {}
82-
gt_path = 'data/MOT17/MOT17DetLabels/train/' + ann['folder'] + '/gt/gt.txt'
83-
with open(gt_path) as f:
84-
lines = f.readlines()
85-
for line in lines:
86-
frame, tid, xmin, ymin, width, height, score, class_id, visibility = line.rstrip('\n').split(',')
87-
if frame not in xml_data:
88-
xml_data[frame] = []
89-
obj = {}
90-
obj['trackid'] = tid
91-
obj['xmin'] = xmin
92-
obj['ymin'] = ymin
93-
obj['xmax'] = str(int(xmin) + int(width))
94-
obj['ymax'] = str(int(ymin) + int(height))
95-
obj['name'] = class_id
96-
xml_data[frame].append(obj)
81+
for ann in anns:
82+
xml_data = {}
83+
gt_path = ann_dir + ann['folder'] + '/gt/gt.txt'
84+
with open(gt_path) as f:
85+
lines = f.readlines()
86+
for line in lines:
87+
frame, tid, xmin, ymin, width, height, score, class_id, visibility = line.rstrip('\n').split(',')
88+
if frame not in xml_data:
89+
xml_data[frame] = []
90+
obj = {}
91+
obj['trackid'] = tid
92+
obj['xmin'] = xmin
93+
obj['ymin'] = ymin
94+
obj['xmax'] = str(int(xmin) + int(width))
95+
obj['ymax'] = str(int(ymin) + int(height))
96+
obj['name'] = class_id
97+
xml_data[frame].append(obj)
9798

98-
count = 1
99-
length = len(xml_data)
100-
for frame in sorted(xml_data.keys(), key = lambda x: int(x)):
101-
annotation = root(ann['folder'] + '/' + ann['imdir'], frame.zfill(6) + ann['imext'], ann['width'], ann['height'])
102-
for instance in xml_data[frame]:
103-
annotation.append(instance_to_xml(instance))
99+
count = 1
100+
length = len(xml_data)
101+
for frame in sorted(xml_data.keys(), key = lambda x: int(x)):
102+
annotation = root(ann['folder'] + '/' + ann['imdir'], frame.zfill(6) + ann['imext'], ann['width'], ann['height'])
103+
for instance in xml_data[frame]:
104+
annotation.append(instance_to_xml(instance))
104105

105-
if count<=((1-validation_split)*length):
106-
if not os.path.isdir('data/MOT17Ann/train/' + ann['folder']):
107-
os.makedirs('data/MOT17Ann/train/' + ann['folder'])
108-
outfile = 'data/MOT17Ann/train/' + ann['folder'] + '/{}.xml'.format(frame.zfill(6))
109-
etree.ElementTree(annotation).write(outfile, pretty_print=True)
110-
else:
111-
if not os.path.isdir('data/MOT17Ann/val/' + ann['folder']):
112-
os.makedirs('data/MOT17Ann/val/' + ann['folder'])
113-
outfile = 'data/MOT17Ann/val/' + ann['folder'] + '/{}.xml'.format(frame.zfill(6))
114-
etree.ElementTree(annotation).write(outfile, pretty_print=True)
115-
count += 1
106+
if ann_dir.split('/')[-2] == 'train':
107+
if count<=((1-validation_split)*length):
108+
if not os.path.isdir('data/MOT17Ann/train/' + ann['folder']):
109+
os.makedirs('data/MOT17Ann/train/' + ann['folder'])
110+
outfile = 'data/MOT17Ann/train/' + ann['folder'] + '/{}.xml'.format(frame.zfill(6))
111+
etree.ElementTree(annotation).write(outfile, pretty_print=True)
112+
else:
113+
if not os.path.isdir('data/MOT17Ann/val/' + ann['folder']):
114+
os.makedirs('data/MOT17Ann/val/' + ann['folder'])
115+
outfile = 'data/MOT17Ann/val/' + ann['folder'] + '/{}.xml'.format(frame.zfill(6))
116+
etree.ElementTree(annotation).write(outfile, pretty_print=True)
117+
count += 1
118+
else:
119+
if not os.path.isdir('data/MOT17Ann/test/' + ann['folder']):
120+
os.makedirs('data/MOT17Ann/test/' + ann['folder'])
121+
outfile = 'data/MOT17Ann/test/' + ann['folder'] + '/{}.xml'.format(frame.zfill(6))
122+
etree.ElementTree(annotation).write(outfile, pretty_print=True)
116123

117124
if __name__=="__main__":
118125

utility/preprocessing.py

Lines changed: 7 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -279,9 +279,9 @@ def output_from_instance(self, train_instance, idx):
279279
0, 1.2e-3 * img.shape[0],
280280
(0,255,0), 2)
281281

282-
if not os.path.isdir('data/self.debug/' + str(idx)):
283-
os.makedirs('data/self.debug/' + str(idx))
284-
file_path = 'data/self.debug/' + str(idx) + '/' + train_instance['filename'].split('/')[-1]
282+
if not os.path.isdir('data/debug/' + str(idx)):
283+
os.makedirs('data/debug/' + str(idx))
284+
file_path = 'data/debug/' + str(idx) + '/' + train_instance['filename'].split('/')[-1]
285285
cv2.imwrite(file_path, img)
286286

287287
# assign input image to x
@@ -466,9 +466,9 @@ def output_from_instance(self, train_instance, idx):
466466
0, 1.2e-3 * img.shape[0],
467467
(0,255,0), 2)
468468

469-
if not os.path.isdir('data/self.debug/' + str(idx)):
470-
os.makedirs('data/self.debug/' + str(idx))
471-
file_path = 'data/self.debug/' + str(idx) + '/' + train_instance['filename'].split('/')[-1]
469+
if not os.path.isdir('data/debug/' + str(idx)):
470+
os.makedirs('data/debug/' + str(idx))
471+
file_path = 'data/debug/' + str(idx) + '/' + train_instance['filename'].split('/')[-1]
472472
cv2.imwrite(file_path, img)
473473

474474
# assign input to x
@@ -504,5 +504,5 @@ def __getitem__(self, idx):
504504

505505
def on_epoch_end(self):
506506
os.rmdir('data/tmp/')
507-
os.rmdir('data/self.debug/')
507+
os.rmdir('data/debug/')
508508
super(BatchSequenceGenerator2, self).on_epoch_end()

0 commit comments

Comments
 (0)