वायोला-जोन्स के चेहरे का पता लगाने का दावा 180k की विशेषताएं हैं


84

मैं वियोला-जोन्स के फेस डिटेक्शन एल्गोरिदम के एक अनुकूलन को लागू कर रहा हूं । यह तकनीक एक छवि के भीतर 24x24 पिक्सेल की सबफ़्रेम रखने पर निर्भर करती है, और बाद में हर आकार के साथ हर स्थिति में इसके अंदर आयताकार विशेषताओं को रखती है।

इन सुविधाओं में दो, तीन या चार आयत शामिल हो सकते हैं। निम्नलिखित उदाहरण प्रस्तुत है।

आयत की विशेषताएं

वे दावा करते हैं कि संपूर्ण सेट 180k (धारा 2) से अधिक है:

यह देखते हुए कि डिटेक्टर का आधार रिज़ॉल्यूशन 24x24 है, आयत सुविधाओं का संपूर्ण सेट 180,000 से अधिक है। ध्यान दें कि Haar आधार के विपरीत, आयत सुविधाओं का सेट अधूरा है।

निम्नलिखित कथनों को स्पष्ट रूप से कागज में नहीं बताया गया है, इसलिए वे मेरी ओर से मान्य हैं:

  1. केवल 2 दो-आयत सुविधाएँ, 2 तीन-आयत सुविधाएँ और 1 चार-आयत सुविधाएँ हैं। इसके पीछे तर्क यह है कि हम हाइलाइट किए गए आयतों के बीच के अंतर को देख रहे हैं , न कि स्पष्ट रूप से रंग या चमक या उस तरह की किसी भी चीज़ को।
  2. हम 1x1 पिक्सेल ब्लॉक के रूप में सुविधा प्रकार ए को परिभाषित नहीं कर सकते हैं; यह कम से कम 1x2 पिक्सेल का होना चाहिए। इसके अलावा, टाइप डी कम से कम 2x2 पिक्सेल होना चाहिए, और यह नियम अन्य विशेषताओं के अनुसार है।
  3. हम फ़ीचर प्रकार A को 1x3 पिक्सेल ब्लॉक के रूप में परिभाषित नहीं कर सकते क्योंकि मध्य पिक्सेल को विभाजित नहीं किया जा सकता है, और इसे खुद से घटाकर 1x2 पिक्सेल ब्लॉक के समान है; यह सुविधा प्रकार केवल चौड़ाई के लिए भी परिभाषित किया गया है। साथ ही, सुविधा प्रकार C की चौड़ाई 3 से विभाज्य होनी चाहिए, और यह नियम अन्य विशेषताओं के अनुसार है।
  4. हम ०.० की चौड़ाई और / या ऊंचाई के साथ एक सुविधा को परिभाषित नहीं कर सकते हैं, इसलिए हम x और y को २४ शून्य से सुविधा के आकार में बदल देते हैं।

इन मान्यताओं के आधार पर, मैंने संपूर्ण सेट को गिना है:

const int frameSize = 24;
const int features = 5;
// All five feature types:
const int feature[features][2] = {{2,1}, {1,2}, {3,1}, {1,3}, {2,2}};

int count = 0;
// Each feature:
for (int i = 0; i < features; i++) {
    int sizeX = feature[i][0];
    int sizeY = feature[i][1];
    // Each position:
    for (int x = 0; x <= frameSize-sizeX; x++) {
        for (int y = 0; y <= frameSize-sizeY; y++) {
            // Each size fitting within the frameSize:
            for (int width = sizeX; width <= frameSize-x; width+=sizeX) {
                for (int height = sizeY; height <= frameSize-y; height+=sizeY) {
                    count++;
                }
            }
        }
    }
}

परिणाम 162,336 है

एक ही तरीका है कि मैं "180,000 से अधिक" वियोला और जोन्स के बारे में बात करने के लिए पाया, # 4 धारणा को छोड़ रहा है और कोड में बगों को पेश करके। इसमें क्रमशः चार लाइनें बदलना शामिल है:

for (int width = 0; width < frameSize-x; width+=sizeX)
for (int height = 0; height < frameSize-y; height+=sizeY)

परिणाम फिर 180,625 है । (ध्यान दें कि यह प्रभावी रूप से सुविधाओं को कभी भी सबफ़्रेम के दाएं और / या नीचे छूने से रोक देगा।)

अब निश्चित रूप से सवाल: क्या उन्होंने अपने कार्यान्वयन में गलती की है? क्या यह शून्य की सतह के साथ सुविधाओं पर विचार करने के लिए कोई मतलब है? या मैं इसे गलत तरीके से देख रहा हूं?


जब मैं आपका कोड चलाऊंगा तो मुझे १ = ४ =४ =२ क्यों मिलेंगे?
निकी

आपका x / y लूप 1 पर क्यों शुरू होता है? मुझे लगता है कि x / y फीचर आयत का शीर्ष बाएं समन्वय है। X / y को 0/0 से शुरू नहीं करना चाहिए?
निकी

इसके अलावा कि क्या यह 0 या 1 से शुरू होता है, पर समाप्त होने का x < sizeअनुमान # 4 से है: मैं चाहता हूं कि सुविधा सबफ़्रेम के भीतर बनी रहे, लेकिन इसका आयाम कम से कम 1x1 है। जैसे कि क्या सुविधा का आयाम सबफ़्रेम के बाहर नहीं होना चाहिए, ठीक है, शायद यह एक धारणा है।
पॉल लामेरटर्मा

इसी तरह, अगर मैंने x को 0 पर शुरू किया, तो इसे चलाना होगा x < size - 1, इसलिए कोई लाभ नहीं है।
पॉल लामर्ट्समा

मैंने छोरों के लिए एक ज़िलिन किया है। यह मुझे गलत लगता है। <आकार x को कभी 24 बनने से रखेगा, 0 से शुरू होकर आपको 0 ... 23 देगा, 1 पिक्सेल चौड़ा होने के साथ, आयत कभी भी फ्रेम को नहीं छोड़ेगी।
ब्रेटन

जवाबों:


40

करीब से देखने पर, आपका कोड मुझे सही लगता है; जिससे एक आश्चर्य होता है कि क्या मूल लेखकों के पास एक-एक बग था। मुझे लगता है कि किसी को यह देखना चाहिए कि OpenCV इसे कैसे लागू करता है!

फिर भी, एक सुझाव यह समझने में अधिक आसान बनाने के लिए के आदेश फ्लिप करने के लिए है के लिए पहले सभी आकार के ऊपर जा रहा है, तो संभावित स्थानों से अधिक पाशन आकार दिया द्वारा छोरों:

#include <stdio.h>
int main()
{
    int i, x, y, sizeX, sizeY, width, height, count, c;

    /* All five shape types */
    const int features = 5;
    const int feature[][2] = {{2,1}, {1,2}, {3,1}, {1,3}, {2,2}};
    const int frameSize = 24;

    count = 0;
    /* Each shape */
    for (i = 0; i < features; i++) {
        sizeX = feature[i][0];
        sizeY = feature[i][1];
        printf("%dx%d shapes:\n", sizeX, sizeY);

        /* each size (multiples of basic shapes) */
        for (width = sizeX; width <= frameSize; width+=sizeX) {
            for (height = sizeY; height <= frameSize; height+=sizeY) {
                printf("\tsize: %dx%d => ", width, height);
                c=count;

                /* each possible position given size */
                for (x = 0; x <= frameSize-width; x++) {
                    for (y = 0; y <= frameSize-height; y++) {
                        count++;
                    }
                }
                printf("count: %d\n", count-c);
            }
        }
    }
    printf("%d\n", count);

    return 0;
}

पिछले परिणाम के समान 162336


इसे सत्यापित करने के लिए, मैंने 4x4 विंडो के मामले का परीक्षण किया और मैन्युअल रूप से सभी मामलों की जांच की (1x2 / 2x1 और 1x3 / 3x1 आकृतियों की गणना केवल 90 डिग्री घुमाई गई):

2x1 shapes:
        size: 2x1 => count: 12
        size: 2x2 => count: 9
        size: 2x3 => count: 6
        size: 2x4 => count: 3
        size: 4x1 => count: 4
        size: 4x2 => count: 3
        size: 4x3 => count: 2
        size: 4x4 => count: 1
1x2 shapes:
        size: 1x2 => count: 12             +-----------------------+
        size: 1x4 => count: 4              |     |     |     |     |
        size: 2x2 => count: 9              |     |     |     |     |
        size: 2x4 => count: 3              +-----+-----+-----+-----+
        size: 3x2 => count: 6              |     |     |     |     |
        size: 3x4 => count: 2              |     |     |     |     |
        size: 4x2 => count: 3              +-----+-----+-----+-----+
        size: 4x4 => count: 1              |     |     |     |     |
3x1 shapes:                                |     |     |     |     |
        size: 3x1 => count: 8              +-----+-----+-----+-----+
        size: 3x2 => count: 6              |     |     |     |     |
        size: 3x3 => count: 4              |     |     |     |     |
        size: 3x4 => count: 2              +-----------------------+
1x3 shapes:
        size: 1x3 => count: 8                  Total Count = 136
        size: 2x3 => count: 6
        size: 3x3 => count: 4
        size: 4x3 => count: 2
2x2 shapes:
        size: 2x2 => count: 9
        size: 2x4 => count: 3
        size: 4x2 => count: 3
        size: 4x4 => count: 1

यह समझाते हुए कि। इसलिए मुझे विश्वास है कि मुझे पूरा यकीन है कि हम सही हैं। मैंने लेखक को ई-मेल भेजा है यह देखने के लिए कि क्या मैंने अपने तर्क में कुछ मौलिक गलती की है। हम देखेंगे कि क्या व्यस्त रहने वाले व्यक्ति के पास प्रतिक्रिया देने का समय है।
पॉल लामर्ट्स्मा 22

इस बात को ध्यान में रखते हुए कि यह एक-दो साल से बाहर है, और तब से कई सुधार किए गए हैं
अमरो नो

25
मूल कागज जहां 180k कहा गया था वह 2001 के सम्मेलन के लिए कंप्यूटर विजन और पैटर्न मान्यता की कार्यवाही से आता है। एक संशोधित पेपर, जिसे 2003 में स्वीकार किया गया और 2004 में इंटरनेशनल जर्नल ऑफ़ कंप्यूटर विज़न में प्रकाशित किया गया, पी पर लिखा गया। 139 (धारा 2 का अंत): "आयतों का संपूर्ण सेट काफी बड़ा है, 160,000"। लगता है हम सही थे!
पॉल लामर्ट्स्मा

3
महान, अद्यतन के लिए धन्यवाद। रुचि रखने वालों के लिए, मुझे IJCV'04 पेपर का एक लिंक मिला: lear.inrialpes.fr/people/triggs/student/vj/viola-ijcv04.pdf
अमरो

हाँ बस यही। 160k, 180k नहीं।
पॉल लामेरत्स्मा 14

9

सब। वियोला और जोन्स के कागजात में अभी भी कुछ भ्रम है।

उनके CVPR'01 पेपर में यह स्पष्ट रूप से कहा गया है कि

"अधिक विशेष रूप से, हम तीन प्रकार की विशेषताओं का उपयोग करते हैं । दो-आयत सुविधा का मान दो आयताकार क्षेत्रों के भीतर पिक्सेल के योग के बीच का अंतर है। क्षेत्रों का आकार और आकार समान है और क्षैतिज या लंबवत आसन्न हैं (चित्र देखें) 1)। एक तीन-आयत सुविधा एक केंद्र आयत में योग से घटाए गए दो आयतों के भीतर योग की गणना करती है। अंत में एक चार-आयत विशेषता "।

IJCV'04 पेपर में, ठीक यही बात कही गई है। तो कुल मिलाकर, 4 सुविधाएँ । लेकिन अजीब तरह से, उन्होंने इस बार कहा कि संपूर्ण सुविधा सेट 45396 है! यह अंतिम संस्करण नहीं लगता है। मुझे लगता है कि कुछ अतिरिक्त बाधाओं को वहां पेश किया गया था, जैसे कि min_width, min_height, चौड़ाई / ऊंचाई अनुपात, और यहां तक ​​कि स्थिति।

ध्यान दें कि दोनों पेपर उसके वेबपेज पर डाउनलोड करने योग्य हैं ।


3

पूरे पेपर को न पढ़ने के बाद, आपकी बोली का शब्दांकन मुझ पर हावी हो गया

यह देखते हुए कि डिटेक्टर का आधार रिज़ॉल्यूशन 24x24 है, आयत सुविधाओं का संपूर्ण सेट 180,000 से अधिक है। ध्यान दें कि Haar आधार के विपरीत, आयत सुविधाओं का सेट अधूरा है।

"आयत सुविधाओं का सेट अधूरा है" "व्यापक सेट"

यह मुझे एक सेट अप की तरह लगता है, जहां मैं पेपर लेखक से अपेक्षा करता हूं कि वे इस स्पष्टीकरण के साथ कि वे खोज स्पेस को अधिक प्रभावी सेट तक कैसे ले जाते हैं, उदाहरण के लिए, शून्य के साथ आयतों जैसे तुच्छ मामलों से छुटकारा पाएं। सतह क्षेत्र।

संपादित करें: या अमूर्त संकेत के रूप में मशीन लर्निंग एल्गोरिथ्म के किसी प्रकार का उपयोग करना। थकाऊ सेट से तात्पर्य सभी संभावनाओं से है, न कि केवल "उचित" से।


मुझे "अधूरा" के बाद फुटनोट शामिल करना चाहिए: "एक पूर्ण आधार में आधार तत्वों के बीच कोई रैखिक निर्भरता नहीं है और इसमें छवि स्थान के समान तत्व हैं, इस मामले में 576। 180,000 हजार सुविधाओं का पूरा सेट कई बार खत्म हो गया है- पूर्ण।" वे स्पष्ट रूप से बिना किसी सतह वाले क्लासिफायर से छुटकारा नहीं पाते हैं, वे यह निर्धारित करने के लिए AdaBoost का उपयोग करते हैं कि "इन विशेषताओं की एक बहुत छोटी संख्या को एक प्रभावी क्लासिफायरियर बनाने के लिए जोड़ा जा सकता है"। ठीक है, इसलिए शून्य-सतह सुविधाओं को तुरंत गिरा दिया जाएगा, लेकिन उन्हें पहले स्थान पर क्यों माना जाता है?
पॉल लामर्ट्स्मा 12

वैसे यह किसी को वास्तव में सेट सिद्धांत में तर्क करने जैसा लगता है।
ब्रेटन

मैं मानता हूं, संपूर्ण सेट से सभी संभावनाएं प्रभावित होंगी। लेकिन विचार करें कि यदि आप x और चौड़ाई <= x के लिए 1 से 24 लेते हैं , तो सुविधा सबफ़्रेम के बाहर 1 पिक्सेल का विस्तार करेगी!
13

क्या आप सुनिश्चित हैं कि आपका कोड "एक-एक करके" कीड़े से नहीं भरा है? मुझे बस एक करीब से देखना था, और आपको यकीन है कि लूप के लिए लिखने का एक अजीब तरीका है।
ब्रेटन

मुझे इस योग्य होना चाहिए- मैंने अभी इसे थोड़ा सा सोचा है, और यदि आपके पास एक आयत है जो 1 पिक्सेल लंबा, 2 पिक्सेल लंबा, 3 पिक्सेल लंबा है, सभी 24 पिक्सेल लंबा है, तो आपके पास 24 प्रकार के आयत हैं, सभी जो एक 24 पिक्सेल हाई सबफ्रेम में फिट होता है। क्या ओवरहांग?
ब्रेटन

2

इस बात की कोई गारंटी नहीं है कि किसी भी पेपर का कोई भी लेखक अपनी सभी धारणाओं और निष्कर्षों में सही है। यदि आपको लगता है कि धारणा # 4 मान्य है, तो उस धारणा को बनाए रखें, और अपने सिद्धांत को आज़माएं। आप मूल लेखकों की तुलना में अधिक सफल हो सकते हैं।


प्रयोग से पता चलता है कि यह ठीक वैसा ही प्रतीत होता है। मेरा मानना ​​है कि AdaBoost केवल पहले चक्र में उन अतिरिक्त शून्य-सतह सुविधाओं को गिरा देता है, लेकिन मैंने वास्तव में इस पर ध्यान नहीं दिया है।
पॉल लामर्ट्स्मा

कंप्यूटर की दृष्टि में वायोला और जोन्स बहुत बड़े नाम हैं। वास्तव में, इस विशेष पेपर को सेमिनल माना जाता है। हर कोई गलती करता है, लेकिन यह विशेष एल्गोरिथ्म बहुत अच्छी तरह से काम करने के लिए सिद्ध हुआ है।
दिमा

1
निश्चित रूप से, और मुझे उनकी विधि पर बिल्कुल भी संदेह नहीं है। यह कुशल है और बहुत अच्छी तरह से काम करता है! सिद्धांत ध्वनि है, लेकिन मेरा मानना ​​है कि उन्होंने गलती से अपने डिटेक्टर को एक पिक्सेल छोटा और अनावश्यक शून्य-सतह सुविधाओं को शामिल किया हो सकता है। यदि नहीं, तो मैं आपको 180k सुविधाओं को प्रदर्शित करने के लिए चुनौती देता हूं!
पॉल लामर्ट्समा

तथ्य यह है कि हर कोई इंसान है। गलतियां सबसे होती हैं। जब कोई बड़ा नाम गलती करता है, तो वे अक्सर पीढ़ियों के लिए छिपे रहते हैं क्योंकि लोग प्राप्त ज्ञान पर सवाल उठाने से डरते हैं। लेकिन सच्चा विज्ञान, वैज्ञानिक पद्धति का अनुसरण करता है और किसी की भी पूजा नहीं करता, चाहे उनका नाम कितना भी बड़ा क्यों न हो। यदि यह विज्ञान है, तो मात्र नश्वर प्रयास में डाल सकते हैं, समझें कि यह कैसे काम करता है और इसे उनकी परिस्थितियों के अनुकूल बनाता है।
माइकल डिलन

हम देखेंगे; मैंने लेखक को एक ई-मेल भेजा है।
पॉल लामेरट्स्मा

1

काफी अच्छा अवलोकन, लेकिन वे शून्य-पैड को 24x24 फ्रेम, या "अतिप्रवाह" कह सकते हैं और पहले पिक्सल का उपयोग करना शुरू कर सकते हैं जब यह सीमा से बाहर हो जाता है, जैसा कि घूर्णी पारियों में, या जैसा कि ब्रेटन ने कहा कि वे कुछ सुविधाओं को "तुच्छ सुविधाओं" के रूप में मान सकते हैं। और फिर उन्हें AdaBoost के साथ छोड़ दें।

इसके अलावा, मैंने आपके कोड के पायथन और मैटलैब संस्करणों को लिखा है ताकि मैं खुद कोड का परीक्षण कर सकूं (मेरे लिए आसान और मेरे लिए अनुसरण करना) और इसलिए मैं उन्हें यहां पोस्ट करूं यदि कोई उन्हें किसी समय उपयोगी लगता है।

अजगर:

frameSize = 24;
features = 5;
# All five feature types:
feature = [[2,1], [1,2], [3,1], [1,3], [2,2]]

count = 0;
# Each feature:
for i in range(features):
    sizeX = feature[i][0]
    sizeY = feature[i][1]
    # Each position:
    for x in range(frameSize-sizeX+1):
        for y in range(frameSize-sizeY+1):
            # Each size fitting within the frameSize:
            for width in range(sizeX,frameSize-x+1,sizeX):
                for height in range(sizeY,frameSize-y+1,sizeY):
                    count=count+1
print (count)

Matlab:

frameSize = 24;
features = 5;
% All five feature types:
feature = [[2,1]; [1,2]; [3,1]; [1,3]; [2,2]];

count = 0;
% Each feature:
for ii = 1:features
    sizeX = feature(ii,1);
    sizeY = feature(ii,2);
    % Each position:
    for x = 0:frameSize-sizeX
        for y = 0:frameSize-sizeY
            % Each size fitting within the frameSize:
            for width = sizeX:sizeX:frameSize-x
                for height = sizeY:sizeY:frameSize-y
                    count=count+1;
                end
            end
        end
    end
end

display(count)

आप 5 सुविधाओं का उपयोग क्यों करते हैं, केवल 4 मुख्य प्रश्न में पोस्ट किए गए हैं। लेकिन अजगर संस्करण के लिए वैसे भी धन्यवाद।
कास्परोवॉव

0

अपने मूल 2001 के पेपर में वे केवल यह कहते हैं कि तीन प्रकार की सुविधाओं का उपयोग किया जाता है:

हम तीन प्रकार की सुविधाओं का उपयोग करते हैं

भी

क्षेत्रों का आकार और आकार समान है

चूंकि प्रत्येक प्रकार में दो झुकाव होते हैं, इसलिए यह मान लेना उचित है कि वे कुल में 6 सुविधाओं का उपयोग करते हैं (कम से कम सुविधाओं की कुल संख्या के लिए): 2 दो-आयत सुविधाएँ, 2 तीन-आयत सुविधाएँ और 2 चार-आयत सुविधाएँ। इस धारणा के साथ वास्तव में 180,000 से अधिक विशेषताएं हैं:

feature_types = [(1,2), (2,1), (1,3), (3,1), (2,2), (2,2)]
window_size = (24,24)

total_features = 0
for f_type in feature_types:
    for f_height in range(f_type[0], window_size[0] + 1, f_type[0]):
        for f_width in range(f_type[1], window_size[1] + 1, f_type[1]):
            total_features += (window_size[0] - f_height + 1) * (window_size[1] - f_width + 1)
            
print(total_features)
# 183072

यदि आप एक चार-आयत प्रकार की सुविधाओं को छोड़ देते हैं (जो उनके बाद के प्रकाशन में मामला लगता है), तो कुल सुविधाओं की संख्या 162,336 है।

हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.