我有一个视频https://www.youtube.com/watch?v=LdNrXndwyCc。 我正在尝试计算此视频中的未知人数,但有以下限制:
问题:
一个人微笑或将其脸从前向左(或从前向右)旋转时,它将检测到该脸为新脸并增加未知数
几帧后无法正确检测到新面孔
在Python3,opencv2,face_recognition python的库中尝试过。平台Ubuntu 18.04
class FaceCount:
def __init__(self):
self.unknown_count=0
def face_distance_to_conf(self,face_distance, face_match_threshold=0.6):
if face_distance > face_match_threshold:
range = (1.0 - face_match_threshold)
linear_val = (1.0 - face_distance) / (range * 2.0)
return linear_val
else:
range = face_match_threshold
linear_val = 1.0 - (face_distance / (range * 2.0))
return linear_val + ((1.0 - linear_val) * math.pow((linear_val - 0.5) * 2, 0.2))
def countFaceThread(self,facelist,face_encodings):
matched_with_no_one=True
for face_encoding in face_encodings:
dup=False
for face in facelist:
match=face_recognition.compare_faces([face_encoding],face)[0]
face_distanc=face_recognition.face_distance([face_encoding],face)
percent=self.face_distance_to_conf(face_distanc)[0]
print(percent)
if match and percent>0.40:
dup=True
matched_with_no_one=False
break
#print('finished Comparing')
if not dup:
self.unknown_count+=1
print("unknown_count---->",self.unknown_count)
facelist.append(face_encoding)
if matched_with_no_one:
print("clearing facelist....")
facelist.clear()
print("unknown_count---->",self.unknown_count)
for f_encode in face_encodings:
facelist.append(f_encode)
def countUnknown(self):
cap = cv2.VideoCapture('livetest.webm')
cap.set(cv2.CAP_PROP_POS_MSEC,30)
facelist=[]
while(cap.isOpened()):
try:
#istart=time.time()
ret, frame = cap.read()
#print('frame reading time------->',time.time()-istart)
#start=time.time()
rgb_frame = frame[:, :, ::-1]
face_locations = face_recognition.face_locations(rgb_frame)
face_encodings = face_recognition.face_encodings(rgb_frame, face_locations)
#print("detection time----------->",time.time()-start)
#start=time.time()
cv2.imshow('frame', frame)
for (top, right, bottom, left) in face_locations:
cv2.rectangle(frame, (left, top), (right, bottom), (0, 0, 255), 2)
cv2.imshow('frame', frame)
#print("showing the detected frame time----------->",time.time()-start)
start=time.time()
if facelist and face_encodings:
t2=threading.Thread(target=self.countFaceThread,args=(facelist,face_encodings))
t2.start()
elif face_locations:
self.unknown_count+=len(face_locations)
print("unknown people------->",self.unknown_count)
for face in face_encodings:
facelist.append(face)
continue
if cv2.waitKey(1) & 0xFF == ord('q'):
break
except Exception as e:
print(e)
# When everything done, release the capture
cap.release()
cv2.destroyAllWindows()
if __name__=='__main__':
t1=threading.Thread(target=FaceCount().countUnknown)
t1.start()
https://www.youtube.com/watch?v=LdNrXndwyCc 播放这部影片 在0.02秒内,该人员应被视为未知人员,并将计数增加一。但事实并非如此。当人微笑时会增加
答案 0 :(得分:2)
这不是python版本的问题。您要解决的问题非常具有挑战性。问题在于检测和关联部分。首先,您可能没有检测到,其次,检测到的对象可能未与下一帧关联。
match=face_recognition.compare_faces([face_encoding],face)[0]
face_distanc=face_recognition.face_distance([face_encoding],face)
目标之间的距离太大或太小。您将拥有失败的关联和错误的关联。在这种情况下,您很可能必须通过获得更好的距离函数/人脸编码功能来提高人脸特征关联的准确性。
结合您可以以最小的努力来改善结果的事情。
代替
frame1->检测->关联
frame2->检测->关联
frame3->检测->关联
。 ...
尝试
frame1->检测->跟踪
frame2->检测->跟踪->关联
frame3->检测->跟踪->关联
跟踪可以是任何方法,例如kct或tld跟踪器。它最初是作为单独的跟踪器实现的,有些工作将它们扩展为多个目标跟踪器。您可以在github中找到它们
如图所示,即使您有多人,也会减少假同事或失败同事的人数。
您可以尝试的另一件事是对场景使用骨骼检测/跟踪/关联,坦率地说,我无法真正区分左男孩和右男孩。特别是当它们不直接面对相机时,可能会出现多种检测/跟踪/关联失败的情况。
但是,在骨架检测中,我们确实经常遇到这种类型的姿势/检测/关联问题,人们可以一直移动,跳舞和改变姿势。 github中也有许多开源框架检测跟踪包。
取决于您要为此付出多少努力,可能会有许多其他解决方案。