2009-02-25 17 views
6

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

wikipedia article रिज डिटेक्शन के बारे में गणित का एक गुच्छा है, लेकिन इस तरह से यह प्रोग्रामर के रूप में मेरी मदद नहीं करता है (नहीं कि मैं गणित के विपरीत हूं, लेकिन यह मेरा क्षेत्र नहीं है, और मुझे समझ में नहीं आता कोड में उनके अंतर समीकरणों का अनुवाद कैसे करें)। वास्तव में इसे लागू करने के लिए कोई अच्छा स्रोत है? या, उस मामले के लिए, क्या एक अच्छा ओपन सोर्स कार्यान्वयन है?

संपादित करें: यहां सरल उदाहरण है। हम एक सरल रेखा के साथ शुरू:

http://img24.imageshack.us/img24/8112/linez.th.png

और कैनी एल्गोरिथ्म चलाने पाने के लिए:

http://img12.imageshack.us/img12/1317/canny.th.png

(जैसा कि आप देख सकते हैं कि यह यहाँ मोटा है - अगर आप पर क्लिक करें छवि, आप देखेंगे कि यह वास्तव में दो निकटवर्ती रेखाओं के बीच एक खाली है)

इसके अलावा, मैं लिख रहा हूँ सी ++ में जी, लेकिन यह वास्तव में कोई फर्क नहीं पड़ता। लेकिन मैं एल्गोरिदम को कोड करना चाहता हूं, न केवल SomePackage::findRidges() लिखें और इसके साथ किया जाए।

+0

में आप कौन सी भाषा लिख ​​रहे हैं में सभी पंक्तियां (सेगमेंट नहीं) पाएंगे? Matlab में ऐसे फ़ंक्शन हैं जो बस इसे संभालते हैं। मुझे आश्चर्य होगा अगर आर के पास भी नहीं है। –

+0

सी ++, लेकिन मैं एल्गोरिदम की तलाश में हूं! –

+0

मुझे लगता है कि रिज खोजने की समस्या के बजाए आपको थ्रेसहोल्डिंग समस्या मिली है। –

उत्तर

5

शायद आपको कैनी जैसी किनारे की पहचान के बजाए आपके पास पहले से मौजूद लाइन को साफ करने के मामले में सोचने की आवश्यकता है। ऐसा लगता है कि आपको image morphology के साथ कुछ करने में सक्षम होना चाहिए, विशेष रूप से मैं कंकालटाइज़ और परम एरोडेड पॉइंट टाइप ऑपरेशंस के बारे में सोच रहा हूं। उचित रूप से इन्हें आपकी छवि से हटाई जानी चाहिए जो कि 'लाइन' नहीं हैं - मुझे विश्वास है कि वे इंटेल की ओपनसीवी लाइब्रेरी में लागू किए गए हैं।

आप एक विलुप्त ऑपरेशन का उपयोग करके कैनी फ़िल्टर का उपयोग करके उत्पन्न अपनी डबल लाइन से एक लाइन को पुनर्प्राप्त कर सकते हैं जिसके बाद 3 इरोड (मैंने इसे छविजे में बाहर करने की कोशिश की) - इससे किसी भी किनारों को भी हटाया जाना चाहिए।

2

मैं इयान ने अपनी लाइनों की सफाई करने का सुझाव देने जा रहा था, लेकिन यदि आप ऐसा नहीं करना चाहते हैं, तो आप एक आटा परिवर्तन के कुछ प्रकार को भी देख सकते हैं।

http://en.wikipedia.org/wiki/Hough_transform

ताकि आप इसे के रूप में पतली या मोटी आप की तरह के रूप में कर सकते हैं आप, इस से लाइन के लिए वास्तविक समीकरण प्राप्त करने में सक्षम होना चाहिए। एकमात्र मुश्किल हिस्सा यह पता लगा रहा है कि रेखा कहां समाप्त होती है।

मैटलैब में लिखे गए कुछ साल पहले एक आटा बदलने के लिए मैंने जो कोड लिखा था, वह यहां दिया गया है। मुझे यकीन नहीं है कि यह अब कितना अच्छा काम करता है, लेकिन यह आपको एक सामान्य विचार देना चाहिए। यह एक छवि

im = imread('cube.tif'); 
[bin1,bin2,bin3] = canny(im); 

%% define constants 
binary = bin1; 
distStep = 10; % in pixels 
angStep = 6; % in degrees 
thresh = 50; 

%% vote 
maxDist = sqrt((size(binary,1))^2+(size(binary,2))^2); 
angLoop = 0:angStep*pi/180:pi; 
origin = size(binary)/2; 
accum = zeros(ceil(maxDist/distStep)+1,ceil(360/angStep)+1); 

for y=1:size(binary,2) 
    for x=1:size(binary,1) 
    if binary(x,y) 
     for t = angLoop 
     dx = x-origin(1); 
     dy = y-origin(2); 
     r = x*cos(t)+y*sin(t); 
     if r < 0 
      r = -r; 
      t = t + pi; 
     end 
     ri = round(r/distStep)+1; 
     ti = round(t*180/pi/angStep)+1; 
     accum(ri,ti) = accum(ri,ti)+1; 
     end 
    end 
    end 
end 
imagesc(accum); 

%% find local maxima in accumulator 
accumThresh = accum - thresh; 
accumThresh(logical(accumThresh<0)) = 0; 
accumMax = imregionalmax(accumThresh); 
imagesc(accumMax); 

%% calculate radius & angle of lines 
dist = []; 
ang = []; 
for t=1:size(accumMax,2) 
    for r=1:size(accumMax,1) 
    if accumMax(r,t) 
     ang = [ang;(t-1)*angStep/180*pi]; 
     dist = [dist;(r-1)*distStep]; 
    end 
    end 
end 
scatter(ang,dist); 
+0

मैं पहले से ही यह कर रहा हूं - समस्या यह है कि कैनी एल्गोरिदम डबल किनारों को देता है, जैसा कि मैंने वर्णन किया है। तो मुझे एक बेहतर चरण # 1 की आवश्यकता है :) –

+0

ठीक है, अगर आपकी सभी छवियां इस तरह दिखती हैं, तो आप चरण 1 को छोड़ सकते हैं। अन्यथा, यदि आप वास्तविक छवि का उपयोग कर रहे हैं, तो आपके पास पतली रेखाएं नहीं होनी चाहिए, और कैनी आपको कोई समस्या नहीं देनी चाहिए, नहीं? सिर्फ एक विचार। – mpen

+0

मेरा मानना ​​है कि जेसी की समस्या यह है कि रिज लाइन को * मार्क * कैसे करें, इसके बाद आप लाइन के पैरामीटर प्राप्त करने के लिए हफ़ ट्रांसफॉर्म लागू कर सकते हैं लेकिन यह उनका मुद्दा नहीं है। – jasxun

संबंधित मुद्दे