5

पर दो वर्गों के योग की वर्ग रूट के लगभग अनुमान लगाकर मैं मजेदार के लिए 8-बिट माइक्रोकंट्रोलर (एचसीएस 08) पर असेंबली में एक एफएफटी एल्गोरिदम लागू करने पर काम कर रहा हूं। एक बार एल्गोरिदम पूरा हो जाने के बाद, मेरे पास 8-बिट वास्तविक/काल्पनिक जोड़े की एक सरणी होगी, और मैं इन मानों में से प्रत्येक का परिमाण खोजना चाहूंगा। यही है, अगर एक्स जटिल है, मैं खोजने के लिएमाइक्रोकंट्रोलर

|x| = sqrt(Re{x}^2 + Im{x}^2) 

अब मैं एक 16-बिट रजिस्टर और एक 8 बिट रजिस्टर मेरे पास उपलब्ध है चाहता हूँ। मैंने सोचा कि उन्हें केवल स्क्वायर करना, उन्हें जोड़ना, और परिणाम की वर्ग जड़ लेना, लेकिन यह एक समस्या है: दो 8-बिट संख्याओं के वर्गों के योग का अधिकतम संभव मूल्य ~ 130k है, जो कि उससे बड़ा है 16-बिट रजिस्टर अधिकतम मूल्य (65.5k) हो सकता है।

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

संक्षेप में: कहें कि मेरे पास दो 8-बिट घटकों वाला वेक्टर है, और मैं वेक्टर की लंबाई ढूंढना चाहता हूं। वास्तव में वर्गों और वर्ग की जड़ों की गणना किए बिना मैं इसका अनुमान कैसे लगा सकता हूं?

धन्यवाद!

+1

कॉरडिक कलन विधि का उपयोग फ़ंक्शन (http://en.wikipedia.org/wiki/CORDIC) कुछ नए वेक्टर '' (या समतुल्य करने के लिए एक वेक्टर '' को घुमाने के लिए इस्तेमाल किया जा सकता धीरे-धीरे '<0,y1>'। 'x1' (या' y1') मूल वेक्टर की परिमाण देता है, और कॉर्डिक को बिना किसी गुणा के कार्यान्वित किया जा सकता है। हालांकि मैंने इसे कभी नहीं किया है, और मुझे नहीं पता कि यह कितना मुश्किल है। – mtrw

+0

क्या यह किसी भी मौके से ऑडियो के लिए है? क्या आप डीबी मूल्य प्राप्त करने के लिए बाद में लॉग 10 की गणना करने जा रहे हैं? –

+0

उद्देश्य पर निर्भर करता है: आप लंबाई की जरूरत है, वहाँ कोई दूसरा रास्ता नहीं है तो गणना करने के लिए है, लेकिन जब आप rellly आदर्श की जरूरत है (जो आमतौर पर लंबाई है), तो आप, कि डिफ़ॉल्ट एल 2 आदर्श के बजाय एक और नोर्मा इस्तेमाल कर सकते हैं जैसे मैनहट्टन दूरी (= | वास्तविक | + | कल्पना |)। – flolo

उत्तर

3

यदि योग 65535 से अधिक है, तो इसे 4 (विभाजित दाएं 2 बिट्स) से विभाजित करें, वर्ग रूट लें, और 2 से गुणा करें। आप एक बिट सटीकता खो देंगे, और स्वाभाविक रूप से परिणाम की गारंटी नहीं है 8 बिट्स में फिट करने के लिए।

+0

प्रतिक्रिया के लिए धन्यवाद। मेरी एकमात्र चिंता यह है कि यदि राशि 65535 से अधिक है, तो यह बह जाएगा और मेरे पास जानने का कोई तरीका नहीं होगा। (मैं केवल एक 16-बिट रजिस्टर है, तो दो 16-बिट जोड़कर मिलने अप्रत्याशित परिणाम मिल सकता है।) मुझे लगता है कि मैं शुरू में विभाजित पुन {x} और मैं {x} 2 से, और फिर अंतिम गुणा करके एक ही बात को पूरा कर सकते 2 द्वारा जवाब; क्या यह ध्वनि आपके सुझाव के बराबर है? – user599599

+0

हां, आपका विचार काम करेगा और अपेक्षित परिशुद्धता देता है। – swestrup

+0

आपने पहले से ही यह जवाब स्वीकार कर लिया है, इसलिए मुझे लगता है कि आपने अनुमान लगाया है: इनपुट को 4 से विभाजित करें, और आउटपुट को 2. –

0

ठीक है, आप ध्रुवीय रूप में एक्स लिख सकते हैं:

x = r[cos(w) + i sin(w)] 

जहां w = arctan(Im(x)/Re(x)), तो

|x| = r = Re(x)/cos(w) 

यहां कोई बड़ी संख्या लेकिन हो सकता है आप त्रिकोणमितीय कार्यों पर सटीक खो देंगे (जो है, यदि आपके पास त्रिकोणमितीय कार्यों तक पहुंच है: - /)

+0

हम्म, दिलचस्प विचार से गुणा करें। दुर्भाग्यवश मेरे पास ट्रिगर फ़ंक्शंस तक पहुंच नहीं है, और माइक्रोकंट्रोलर के लिए फ्लोटिंग पॉइंट समर्थन नहीं है, इसलिए मैं मूल पूर्णांक संचालन तक काफी सीमित हूं। मैं हालांकि ट्रिगर लुकअप टेबल रखने की योजना बना रहा हूं, इसलिए मैं इसे ध्यान में रखूंगा। – user599599

6

Fast Magnitude Estimator का वर्णन करने वाला एक वेब पेज है । गुणांक अल्फा और बीटा के लिए

Mag ~= Alpha * max(|I|, |Q|) + Beta * min(|I|, |Q|) 

: मूल विचार एक कम से कम वर्ग (या अन्य उच्च गुणवत्ता) समीकरण के लिए फिट पाने के लिए है। कई गुणांक जोड़े को पूर्ण वर्ग त्रुटियों, अधिकतम त्रुटियों, आदि के साथ सूचीबद्ध किया गया है, जिसमें पूर्णांक एएलयू के लिए उपयुक्त गुणांक शामिल हैं। x |

+0

ऐसा लगता है कि 61/64 विकल्पों में से एक इस एप्लिकेशन के लिए अच्छा होगा। –

0

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

|x| ~ max(|Re{x}|,|Im{x}|) + min(|Re{x}|,|Im{x})/2; 

उपयोग करने के लिए यह जिआदा की कोशिश करेगा | 0 और 12% के बीच कहीं से।

0

यदि आप बाद में डीबी में परिमाण को परिवर्तित करने जा रहे हैं, तो आप sqrt ऑपरेशन के साथ पूरी तरह से वितरण करते हैं। अर्थात।यदि आपके गणना है:

magnitude = sqrt(re*re+im*im); // calculate magnitude of complex FFT output value 
magnitude_dB = 20*log10(magnitude); // convert magnitude to dB 

आप इस रूप में पुनर्लेखन कर सकते हैं:

magnitude_sq = re*re+im*im; // calculate squared magnitude of complex FFT output value 
magnitude_dB = 10*log10(magnitude_sq); // convert squared magnitude to dB 
+0

अच्छा बिंदु, लेकिन मेरी समस्या यह है कि लॉग 10 भी एक कम्प्यूटेशनल महंगा ऑपरेशन है। मुझे अभी भी निकटतम पूर्णांक खोजने या लुकअप टेबल का उपयोग करने की समस्या होगी। – user599599

+0

@ user599599: हाँ, तुम अब भी 'log', लेकिन पहले आप था' sqrt' + 'log' है और अब तुम सिर्फ' log' है। –

0

तुम सिर्फ 2 रजिस्टरों के साथ सीमित हो सकता है, लेकिन आप http://www.realitypixels.com/turk/opensource/index.html फिक्स्ड प्वाइंट वर्ग मूल फिक्स्ड पर इस कोड को देखो सकता है सूत्रीय त्रिकोणमितीय कॉरडिक

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