• 카테고리

    질문 & 답변
  • 세부 분야

    컴퓨터 비전

  • 해결 여부

    해결됨

dnn 얼굴식별 코드 모르겠는 부분이 있습니다.

20.03.24 01:33 작성 조회수 2.4k

3

안녕하세요... haar 는 비교적 쉽게 이해를 했는데 dnn 은 이해가지 않는 부분이 많아 몇 가지 여쭤보려고 합니다. 

첫번째 질문입니다. 

blob = cv2.dnn.blobFromImage(cv2.resize(frame, (300,300)), 1.0, (300, 300), (104.0,177.0, 123.0))

이 코드말인데요. 제가 blobFromImage() 공식문서를 찾아보니까 첫번째 파라미터는 이미지를 넘긴 것 같고, 1.0 이란 건 scale factor 같고, (300,300) 은 size 같고 마지막 파라미터가 mean value 같은데요... 저 값은 도대체 어떻게 알아내서 파라미터로 넘기는거죠? 저 숫자들이 좀 뜬금없고 어디서 나왔는지 모르겠습니다.. 또한 RGB 순인지 BGR 순인지도 알려주세요. 

두번째 질문은

위에 질문이랑 같은 코드에서, 숫자 300 보다 작은 수로 다 바꿔넣으면 에러가 나고 300보다 큰 수로 바꿔넣으면 잘 됩니다. 왜 그런걸까요 ?

그리고 실행했을 때 사진 사이즈가 너무 커서 그런데 좀 줄이려면 어떻게해야돼요?

세번째 질문은

    for i in range(0, detections.shape[2]):

        confidence = detections[0,0,i,2]

이 코드인데.. shape[2] 에서 2 라는 숫자가 뭘 의미하는 거에요? 그리고 그 밑에줄은 아예 무슨 소리인지 이해가 잘 안갑니다. 대괄호 안의 값들 0,0,i,2 가 각각 뭘 의미하는지 모르겠습니다. 이 코드가 detections 들을 쭉 도는 건 직관적으로 이해가 가는데 저 값들이 뭘 의미하는지 모르겠어요.

box = detections[0,0,i,3:7] * np.array([width,height,width,height]) 이 코드도 조금 자세한 설명을 듣고 싶습니다.

마지막 질문은 if 문인데

 y = startY - 10  if  startY - 10 > 10  else  startY + 10

이게 startY-10 > 10 이라면 y = startY-10, 아니라면 startY+10 라는 뜻인건가요? 만약 이거라면

if(startY - 10 > 10) :

    y = startY - 10

else :

    y = startY + 10

이렇게 써야하는 거 아닌가요 ? 

갑자기 내용이 좀 어려워져서 모르는 것도 많아지고 제 이해력도 점점 딸리는 것 같네요...ㅠ 감사합니다 

답변 2

·

답변을 작성해보세요.

1

안녕하세요?

원리까지 열심히 공부하시는 모습이 좋습니다. 

질문하신 부분이 어려운 부분이고 사실 이론적인 설명이 너무길어지면 수강생분들이 지루해질 것 같아서 강의에서는 간단히 설명하고 넘어 갔습니다.

1. cv2.dnn.blobFromImage관련

 - (104.0,177.0, 123.0)는 mean subtraction의 경험적 최적값입니다. 그럼 mean subtractio이 뭔지 이해해야 겠지요. 아래 그림처럼 RGB값의 일부를 제외해서 dnn이 분석하기 쉽게 단순화해주는 것이라 생각하시면 됩니다. 순서는 RGB입니다.

 - (300,300) : dnn모듈이 CNN으로 처리하기 좋은 이미지 사이즈가 있습니다. 224×224227×227, or 299×299..

model_name = 'res10_300x300_ssd_iter_140000.caffemodel'

이 모델은 300으로 이미지 사이즈가 고정되어 있어서 300을 쓰는 것입니다. 

  

 - 사진 사이즈가 너무 커서 그런데 좀 줄이려면 어떻게해야돼요? - 코드에 나온데로 cv2.resize(frame, (300,300))를 사용하면 되겠네요.

2. for i in range(0, detections.shape[2]):관련

 - model(Caffe)에서 이미지를 분석하고 가져온 값을 detections에 넣었습니다.

    그럼 이렇게 출력을 해볼께요.

    print(detections)

    print(detections.shape[2])

    # loop over the detections

    for i in range(0, detections.shape[2]):......

   그러면 detections은

   [[[[0.         1.         0.99986076 ... 0.16988611 0.7576092

    0.77922064]...... 같은 무려 4차 배열로 되어 있고 

    detections.shape[2]를 출력해 보시면 200이라는 값이 출력됩니다.

    이미지를 marathon_02.jpg로 바꾸면 detections값은 바뀌는데 detections.shape[2]은 그대로 200입니다.

    전체 몇개의 박스를 찾아오나보려고 if confidence > 0:라고 고쳐보고 

    아래 print(i, confidence, startX, startY, endX, endY)를 사용해서 보니

    marathon_02.jpg그림은 121까지 그러니까 122개의 박스를 찾아오네요. 

   그러니까 detections.shape[2]는 모델이 가져오는 최대 박스의 갯수라고 보면 됩니다.

-  detections은  [[[[0.         1.         0.99986076 ... 0.16988611 0.7576092

    0.77922064]...... 이렇게 나왔으니 detections[0, 0]을 출력해 볼께요.

   [[0.         1.         0.99986076 ... 0.16988611 0.7576092  0.77922064]....라고 나오네요.

   즉, 우리가 그릴 박스들의 속성들을 가져옵니다. 

   confidence = detections[0, 0, i, 2]라는 루프를 돌때 첫번째 i가 0일때 detections[0, 0]의 첫번째 배열값은

   [0.         1.         0.99986076 ... 0.16988611 0.7576092  0.77922064]을 의미하고 

   이 중 2, 즉 세번째는 0.99986076로 이 박스가 얼굴일 가능성이 99.9%를 넘는다는 것을 의미합니다.

- box = detection[0,0,i,3:7] 라는 루프를 돌때 첫번째i가 0일때 베열 3번부터 7번 이전 즉 6번째 까지 값은 

   0.36570626 0.16988611 0.7576092  0.77922064로 그림의 좌표를 나타냅니다. 

    - 3번째 0.36570626는 전체 폭 중 박스 시작점의 x좌표 상대위치

    - 4번째 0.16988611는 전체 높이 중 박스 시작점의 y좌표 상대위치

    - 5번째  0.7576092는 전체 폭 중 박스 끝점의 x좌표 상대위치

    - 6번째 0.77922064는 전체 높이 중 박스 끝점의 y좌표 상대위치

    그래서 * np.array([width, height, width, height])를 곱해서 (startX, startY, endX, endY)를 구하는 것입니다.

3. y = startY - 10  if  startY - 10 > 10  else  startY + 10관련

  - 이 코드는 쉽게 생각하시면 됩니다. 평소에는 값을 박스 10px위에 표시해 주는데

    혹시라도 박스위에 공간이 10도 안되면   if  startY - 10 > 10

    박스 안 쪽 10밑에 값을 표시하라는 것입니다. startY + 10

건강조심하시고 강의에서 많은 것을 얻어가시길 바랍니다.

감사합니다.

 

0

대박부자님의 프로필

대박부자

2020.03.29

여러 자료 찾아보니 mean을 구하는 방법은 model을 만들때 trainset의 RGB의 데이터로 mean을 만든다고 하네요. 그 값을 우리가 dectection하고자 하는 이미지의 RGB에서 뺌으로써 색깔을 단순화하게 한다고 합니다.