📢 स्तरित कवच
यह लेख हैव्यावहारिक व्यापार के लिए वेवलेट ट्रांसफ़ॉर्म पर एक लोकप्रिय विज्ञानयह कोड एक सरलीकृत शिक्षण संस्करण है (जिसमें बहु-स्तरीय अपघटन, थ्रेशोल्ड डीनोइजिंग और मानक वेवलेट्स के व्युत्क्रम रूपांतरण पुनर्निर्माण जैसे जटिल चरणों को छोड़ दिया गया है), और इसमें केवल मुख्य अवधारणाओं को ही रखा गया है:**रुझान संबंधी जानकारी निकालने के लिए कीमतों पर मल्टी-स्केल स्मूथिंग करने हेतु वेवलेट गुणांकों का उपयोग करें।**यह रणनीति विकास और त्वरित सत्यापन के लिए उपयुक्त है, लेकिन अकादमिक अनुसंधान या शोध पत्र प्रकाशन के लिए नहीं।
I. परिचय: "ज़िहु गुरु" (विशेषज्ञ) के मिथकों का खंडन
जो लोग ज़ीहू पर वित्तीय और मात्रात्मक विषयों को नियमित रूप से ब्राउज़ करते हैं, उन्होंने निश्चित रूप से यह परिदृश्य देखा होगा:
कुछ "विशेषज्ञ" लगातार कहते रहते हैं:
- वेवलेट ट्रांसफॉर्म शोर में कमी
- फूरियर ट्रांसफॉर्म निष्कर्षण अवधि
- लैपलेस स्मूथिंग आउटलायर्स को हटा देता है।
उन्होंने सबको स्तब्ध कर दिया, मानो उन्होंने मात्रात्मक व्यापार के परमाणु हथियार में महारत हासिल कर ली हो।
लेकिन आप चाहते हैं कि वह आपको कोड दिखाए?
"यह... एक व्यापारिक रहस्य है, और मैं इसका खुलासा नहीं कर सकता।"
उनसे इस सिद्धांत को समझाने के लिए कहें।
"इसमें उन्नत गणित शामिल है, अगर मैं आपको समझा भी दूं तो भी आप इसे नहीं समझ पाएंगे।"
आज हम उन विषयों पर चर्चा करेंगे जिनका जिक्र अक्सर इन "ज़िहू विशेषज्ञों" द्वारा किया जाता है, वित्तीय बाजार में वेवलेट ट्रांसफॉर्म के व्यावहारिक अनुप्रयोगों का परिचय देंगे और सभी को इस तकनीक की सही समझ विकसित करने में मदद करेंगे।
II. वेवलेट ट्रांसफॉर्म वास्तव में क्या है?
सरल व्याख्या
कल्पना कीजिए कि आप कोई गाना सुन रहे हैं, लेकिन रिकॉर्डिंग में बैकग्राउंड शोर है:
मूल रिकॉर्डिंग = मानव आवाज + पृष्ठभूमि शोर + स्टैटिक
वेवलेट ट्रांसफॉर्म एक प्रकार का होता है।स्मार्ट फ़िल्टर:
- आवाज को संरक्षित करें
- शोर को फ़िल्टर करें
- यह आपको यह भी बता सकता है कि कौन सा भाग कोरस है और कौन सा भाग छंद है।
वित्तीय बाजार की ओर रुख करें:
मूल कीमत = वास्तविक रुझान + अल्पकालिक उतार-चढ़ाव + यादृच्छिक शोर
वेवलेट ट्रांसफॉर्म आपकी मदद कर सकता है:
- वास्तविक रुझान को निकालना(दीर्घकालिक दिशा)
- अल्पकालिक उतार-चढ़ावों को फ़िल्टर करना(दिन के दौरान होने वाले उतार-चढ़ाव)
- महत्वपूर्ण मोड़ बिंदुओं की पहचान करना(रुझान में उलटफेर)
मुख्य अवधारणा: आधार फ़ंक्शन अपघटन
वेवलेट ट्रांसफॉर्म का सार यह है किमूल सिग्नल को "आधार कार्यों" (वेवलेट्स) के एक विशिष्ट सेट का उपयोग करके विघटित करें।。
मान लीजिए आप किसी व्यक्ति की दिखावट का वर्णन करना चाहते हैं:
- पारंपरिक विधि: पिक्सेल दर पिक्सेल का वर्णन करना, जो बहुत थकाऊ है।
- वेवलेट विधि: "आंखों का आकार, नाक की ऊंचाई और चेहरे की आकृति" जैसे कारकों का उपयोग करना।विशेषताविवरणों को संयोजित करने के लिए
वित्तीय कीमतों में:
मूल मूल्य श्रृंखला = आधार फ़ंक्शन 1 × भार 1 + आधार फ़ंक्शन 2 × भार 2 + ... + शोर
**आधार फलन, तरंग गुणांकों के अनुरूप "टेम्प्लेट" होते हैं।**विभिन्न प्रकार के वेवलेट (हेयर, डाउबेचीज़, मैक्सिकन हैट, आदि) अलग-अलग टेम्पलेट का उपयोग करते हैं, ठीक उसी तरह जैसे कीमतों को विघटित करने के लिए विभिन्न "फीचर एक्सट्रैक्टर" का उपयोग किया जाता है।
फ़िल्टर: आवृत्ति डोमेन में एक छलनी
वेवलेट ट्रांसफॉर्म मूल रूप से एक...मल्टीस्केल फ़िल्टर बैंक:
उच्च आवृत्ति फ़िल्टर → तीव्र उतार-चढ़ाव (दैनिक शोर, टिक-स्तर के उतार-चढ़ाव) को पकड़ता है
मध्यवर्ती आवृत्ति फ़िल्टर → मध्यम अवधि के रुझानों को कैप्चर करता है (कुछ घंटों से लेकर कुछ दिनों तक की अवधि)।
कम आवृत्ति वाले फ़िल्टर → दीर्घकालिक रुझानों (साप्ताहिक और मासिक रुझान) को कैप्चर करते हैं।
इसे "वेवलेट" क्यों कहा जाता है?
- पारंपरिक फूरियर ट्रांसफॉर्म का उपयोग करता हैअनंत लंबी साइन तरंगएक अनंत लंबी रूलर की तरह
- वेवलेट ट्रांसफॉर्म का उपयोग किया जाता हैपरिमित लंबाई वाली "छोटी" तरंगजैसे अलग-अलग लंबाई के स्केल का एक सेट
वित्तीय कीमतों का विश्लेषण करने के लिए साइन तरंगों का उपयोग करने में समस्या यह है: साइन तरंगें यह मानती हैं कि संकेत आवधिक रूप से दोहराया जाता है, लेकिन वित्तीय बाजार ऐसा नहीं करते! बीटीसी आज 10% बढ़ सकता है और कल 8% गिर सकता है, इसमें किसी भी प्रकार की चक्रीयता नहीं होती।
वेवलेट्स के लाभ:स्थानीयकरण विश्लेषणयह आपको बता सकता है कि "20 दिसंबर, 2025 को दोपहर 3 बजे से शाम 5 बजे के बीच कीमतों का रुझान मुख्य रूप से ऊपर की ओर था", न कि "समग्र बाजार में उतार-चढ़ाव हो रहा था" जैसे सामान्य निष्कर्ष के बारे में।
पुनर्निर्माण: विघटन से पुनर्निर्माण तक
वेवलेट ट्रांसफॉर्म हैप्रतिवर्तीयह बहुत महत्वपूर्ण है!
मूल मूल्य ---> वेवलेट अपघटन ---> प्रवृत्ति घटक + अस्थिरता घटक + शोर घटक
ट्रेंड घटक + अस्थिरता घटक + शोर घटक ---> वेवलेट पुनर्निर्माण ---> मूल मूल्य
रिफैक्टरिंग प्रक्रियाइसका उद्देश्य अलग-अलग घटकों को विघटित करना है।चुनिंदा रूप से वापस संयोजित करें:
- ट्रेंड घटक =[99800, 99850, 99900, 99950, ...] # हम क्या चाहते हैं
- उतार-चढ़ाव घटक =[+200, -150, +180, -120, ...] # उपयोगी हो सकता है
- शोर घटक =[±10, ±15, ±8, ±12, ...] # त्याग दें!
पुनर्निर्माण के दौरान केवल ट्रेंड घटकों का उपयोग करें
अपघटन के बाद, निम्नलिखित प्राप्त हुआ
- पुनर्निर्मित मूल्य = प्रवृत्ति घटक + आंशिक अस्थिरता घटक
वास्तविक लेन-देन में, हम आमतौर परकेवल निम्न-आवृत्ति वाले भाग का पुनर्निर्माण करें(प्रवृत्ति) उच्च आवृत्ति वाले घटक (शोर) सीधे हटा दिए जाते हैं। यही वेवलेट "शोर न्यूनीकरण" का सिद्धांत है।
गणित के सिद्धांत (सरलीकृत संस्करण)
चलिए जटिल समाकलन सूत्रों को छोड़ देते हैं और इसे सरल शब्दों में समझाते हैं:
वेवलेट ट्रांसफॉर्म = "वेवलेट गुणांकों" के एक सेट का उपयोग करके मूल्य श्रृंखला का भारित औसत।
मूल सूत्र:
कीमतों को सुचारू बनाना[i] = Σ(मूल कीमत)[i-j] × वेवलेट गुणांक[j]) / Σ(तरंगिका गुणांक)[j])
फ़िल्टर परिप्रेक्ष्य:
मूल मूल्य को वेवलेट फिल्टर के माध्यम से फ़िल्टर किया जाता है → विभिन्न आवृत्तियों के घटकों का चयन किया जाता है।
कुंजी यह हैवेवलेट गुणांकों का चयन:
- विभिन्न तरंगें = विभिन्न फ़िल्टर विशेषताएँ = विभिन्न आवृत्ति प्रतिक्रियाएँ
- विभिन्न स्तर = विभिन्न समय पैमाने = विभिन्न प्रवृत्ति चक्र
उदाहरण के लिए:
यदि आप डाउबेची के 4 वेवलेट का उपयोग करते हैं, तो गुणांक इस प्रकार हैं:[0.483, 0.837, 0.224, -0.129]:
गुणांकों का यह समूह एक फ़िल्टर को परिभाषित करता है:
- सकारात्मक गुणांक (0.483, 0.837, 0.224) → इन पदों के लिए कीमत बनाए रखें।
- ऋणात्मक गुणांक (-0.129) → पहले के मूल्य आंदोलनों को दबाता है
- गुणांक भारण → प्रत्येक मूल्य के योगदान को निर्धारित करता है।
वेवलेट ट्रांसफॉर्म तब पूरा होता है जब आप इस फ़िल्टर को पूरी मूल्य श्रृंखला पर "स्लाइड" करते हैं। प्रत्येक स्लाइड में गणनाएँ शामिल होती हैं।वर्तमान अवधि के भीतर कीमतों का भारित औसतभार तरंग गुणांक हैं।
यह संकेतों को "विघटित" क्यों कर सकता है?
क्योंकि गणितीय रूप से यह सिद्ध किया जा सकता है कि:**किसी भी सिग्नल को वेवलेट बेसिस फंक्शन के रैखिक संयोजन के रूप में दर्शाया जा सकता है।**जिस प्रकार RGB के तीन प्राथमिक रंगों को मिलाकर कोई भी रंग बनाया जा सकता है, उसी प्रकार वेवलेट बेसिस फंक्शन को मिलाकर किसी भी मूल्य श्रृंखला को प्राप्त किया जा सकता है। विभिन्न प्रकार के वेवलेट अलग-अलग "बेसिस फंक्शन लाइब्रेरी" प्रदान करते हैं, जो विभिन्न प्रकार के सिग्नल विश्लेषण के लिए उपयुक्त होते हैं।
III. यह प्रयास: 7 वेवलेट ट्रांसफ़ॉर्म का व्यावहारिक अनुप्रयोग
अनुप्रयोग दृष्टिकोण: सिद्धांत से व्यवहार तक सरलीकरण
सिग्नल प्रोसेसिंग की पाठ्यपुस्तकों में, वेवलेट ट्रांसफॉर्म में आमतौर पर जटिल प्रक्रियाएं शामिल होती हैं...बहुस्तरीय अपघटन, पुनर्निर्माण और थ्रेशोल्ड डीनोइज़िंगचरण:
संपूर्ण वेवलेट विश्लेषण कार्यप्रणाली:
- बहुस्तरीय अपघटन → सन्निकटन गुणांक और विवरण गुणांक उत्पन्न करता है।
- थ्रेशोल्डिंग → शोर को कम करने के लिए विवरण गुणांकों के लिए सॉफ्ट/हार्ड थ्रेशोल्डिंग
- व्युत्क्रम रूपांतरण पुनर्निर्माण → संसाधित गुणांकों को सिग्नल में पुनर्स्थापित करना
- सीमा विस्तार → सिग्नल सीमा प्रभावों का प्रबंधन
- ऊर्जा मानकीकरण → रूपांतरण से पहले और बाद में ऊर्जा संरक्षण सुनिश्चित करता है
लेकिनवित्तीय लेन-देन के व्यावहारिक अनुप्रयोगचीन में हमें इसे इतना जटिल बनाने की आवश्यकता नहीं है। क्योंकि:
1. ट्रेडिंग के लिए केवल ट्रेंड की दिशा जानना आवश्यक है; सटीक पुनर्निर्माण आवश्यक नहीं है।
अकादमिक शोध में पुनर्निर्माण त्रुटि 0.01% से कम होनी चाहिए, लेकिन व्यापार में, यह निर्धारित करने के लिए पर्याप्त है कि कीमत बढ़ेगी या घटेगी। यहां तक कि अगर पुनर्निर्माण में 5% की त्रुटि भी हो, तब भी रणनीति लाभदायक हो सकती है, बशर्ते रुझान की दिशा सही हो।
2. वास्तविक समय की आवश्यकताएं गणनाओं को सरल बनाती हैं।
वेवलेट डीकंपोज़िशन की संपूर्ण प्रक्रिया में गुणांकों की कई परतों की पुनरावर्ती गणना की आवश्यकता होती है, जिससे उच्च-आवृत्ति ट्रेडिंग में विलंब हो सकता है। दूसरी ओर, प्रत्यक्ष कनवोल्यूशन को मिलीसेकंड में पूरा किया जा सकता है, जो लाइव ट्रेडिंग की आवश्यकताओं को पूरा करता है।
3. वित्तीय संकेतों की विशेष विशेषताएं
वित्तीय मूल्य स्थिर संकेत नहीं होते और उनमें कोई निश्चित चक्रीयता नहीं पाई जाती। यहाँ जटिल आवृत्ति विश्लेषण का कोई विशेष महत्व नहीं है; सरल प्रवृत्ति विश्लेषण अधिक व्यावहारिक है।
यह सरलीकरण रणनीति
इसलिए, यह लेखवेवलेट ट्रांसफॉर्म के सार को निकालनावित्तीय बाजारों के सबसे व्यावहारिक पहलुओं पर ध्यान केंद्रित करना:
मुख्य सरलीकरण 1: केवल अनुमानित गुणांकों (निम्न-आवृत्ति प्रवृत्तियों) का उपयोग करें
परंपरागत वेवलेट अपघटन → सन्निकटन गुणांक + विवरण गुणांक (बहु-परत)
यह अनुप्रयोग: केवल अनुमानित गुणांकों को बनाए रखना → सीधे सुव्यवस्थित प्रवृत्ति प्राप्त करना।
कोर सिंपलीफिकेशन 2: थ्रेशोल्डिंग डीनोइजिंग के बिना डायरेक्ट कनवोल्यूशन
परंपरागत वेवलेट अपघटन → विवरण गुणांकों का थ्रेशोल्डिंग → पुनर्निर्माण
यह अनुप्रयोग: प्रत्यक्ष कनवोल्यूशन → सुचारू मूल्य प्राप्त करने के लिए
कोर सरलीकरण 3: सीमा प्रसंस्करण को अनदेखा करें
परंपरागत वेवलेट के लिए सिग्नल सीमाओं के सममित विस्तार और आवधिक विस्तार जैसी प्रक्रियाओं की आवश्यकता होती है।
यह एप्लिकेशन केवल मध्य भाग पर केंद्रित है; सीमा संबंधी त्रुटियां स्वीकार्य हैं।
कार्यान्वयन विधि: फ़िल्टर कनवोल्यूशन
python
def convolve(src, coeffs, step):
"""
核心算法:用小波系数对价格序列做加权平均
src: 价格序列 [100000, 101000, 99000, ...]
coeffs: 小波系数 [0.483, 0.837, 0.224, -0.129]
step: 采样步长(用于多层级)
"""
sum_val = 0.0 # 加权和
sum_w = 0.0 # 权重和
for i, weight in enumerate(coeffs):
idx = i * step
if idx < len(src):
sum_val += src[idx] * weight
sum_w += weight
return sum_val / sum_w # 归一化
यह फ़ंक्शन है...वेवलेट फिल्टर का मूल:
- प्रत्येक कैंडलस्टिक के लिए, यह N कैंडलस्टिक्स (N = वेवलेट गुणांकों की संख्या) को देखता है।
- वेवलेट गुणांकों को भार के रूप में उपयोग करके भारित औसत की गणना करें।
- समायोजन करके
stepपैरामीटर बहु-स्तरीय स्मूथिंग (स्तर 1/2/3...) को सक्षम बनाते हैं।
यह सरलीकरण उचित क्यों है?
क्योंकि लेन-देन की मूलभूत आवश्यकता यह है:शोर में रुझान खोजनावेवलेट ट्रांसफॉर्म के सन्निकटन गुणांक स्वयं सिग्नल के लिए एक "लो-पास फिल्टर" होते हैं, जो निम्न-आवृत्ति प्रवृत्ति घटकों को संरक्षित करते हैं, और यही हमें चाहिए।
हालांकि संपूर्ण वेवलेट विश्लेषण अधिक सटीक है, लेकिन वित्तीय व्यापार में:
- **मुनाफा रुझान की दिशा से आता है।**यह पुनर्निर्माण की सटीकता से नहीं आता है।
- **सरल विधियाँ अधिक मजबूत होती हैं।**जटिल मॉडल ओवरफिटिंग के शिकार होते हैं।
- गणना की गति अधिक महत्वपूर्ण हैवास्तविक व्यापार में, हर मिलीसेकंड पैसा होता है।
डेटा अधिग्रहण: FMZ प्लेटफॉर्म की सुविधा
उपयोगइन्वेंटर क्वांटाइजेशन (FMZ) प्लेटफॉर्म का स्थानीय बैकटेस्टिंग इंजनडेटा प्राप्त करना बहुत सुविधाजनक है!
python
'''backtest
start: 2025-12-17 00:00:00
end: 2025-12-23 08:00:00
period: 1h
basePeriod: 1h
exchanges: [{"eid":"Futures_Binance","currency":"BTC_USDT","fee":[0,0]}]
'''
from fmz import *
task = VCtx(__doc__)
def main():
exchange.SetCurrency("BTC_USDT")
exchange.SetContractType("swap")
records = exchange.GetRecords(PERIOD_H1, 500)
return records
records = main()
किसी जटिल एपीआई एकीकरण या डेटा सफाई की आवश्यकता नहीं है; मानकीकृत कैंडलस्टिक डेटा सीधे प्राप्त किया जा सकता है। इससे हमें डेटा प्रोसेसिंग में उलझने के बजाय सात प्रकार के वेवलेट के वास्तविक प्रभावों को शीघ्रता से सत्यापित करने में मदद मिलती है।
परीक्षण लक्ष्य
क्रिप्टोकरेंसी की कीमतों पर सात सामान्य वेवलेट प्रकारों (हेयर, डाउबेचीज़ 4, सिम्लेट 4, बायोरथोगोनल 3.3, मैक्सिकन हैट, मोर्लेट और डिस्क्रीट मेयर) के प्रदर्शन की तुलना करके, निम्नलिखित दृश्य प्रदर्शन प्रदान किया गया है:
- विभिन्न तरंगों के बीच स्मूथिंग तीव्रता में अंतर
- एक ही वेवलेट के विभिन्न स्तरों पर प्रभाव में भिन्नताएँ
- कौन से वेवलेट अल्पकालिक ट्रेडिंग के लिए उपयुक्त हैं, और कौन से ट्रेंड फॉलो करने के लिए उपयुक्त हैं?
**इसमें गणितीय व्युत्पत्ति की सटीकता पर नहीं, बल्कि व्यावहारिक परिणामों की दृश्य तुलना पर ध्यान केंद्रित किया गया है।**इससे व्यापारियों को सहज समझ विकसित करने और अपनी रणनीति के अनुरूप वेवलेट प्रकार चुनने में मदद मिलती है।
IV. 7 प्रकार की तरंगलेट का विस्तृत विवरण
1. हार वेवलेट - सबसे सरल औसत
हार वेवलेट सबसे बुनियादी प्रकार का वेवलेट है, जिसमें केवल दो गुणांक होते हैं:[0.5, 0.5]असल में, यह दो आसन्न कीमतों का एक साधारण औसत है।
कोर कोड:
python
coeffs = [0.5, 0.5]
# 对价格序列 [100000, 101000, 99000, 102000, 98000] 处理
def smooth(prices, i):
return (prices[i] * 0.5 + prices[i-1] * 0.5) / 1.0
# 结果:[100000, 100500, 100000, 100500, 100000]
जैसा कि आप देख सकते हैं, शुरुआत में अत्यधिक उतार-चढ़ाव वाली कीमत (99,000 से 102,000 तक) हार प्रोसेसिंग के बाद अपेक्षाकृत स्थिर हो जाती है। यह वेवलेट "डीनोइज़िंग" का प्रभाव है - जो अल्पकालिक, तीव्र उतार-चढ़ाव को कम करता है, जिससे आपको एक सहज मूल्य प्रवृत्ति दिखाई देती है।
2. डाउबेचीज़ 4 - इंजीनियरिंग परियोजनाओं में आमतौर पर उपयोग किया जाता है
Daubechies 4 (संक्षेप में db4) इंजीनियरिंग में सबसे अधिक उपयोग किए जाने वाले वेवलेट्स में से एक है। इसके गुणांक इस प्रकार हैं:[0.483, 0.837, 0.224, -0.129]ध्यान दें कि अंतिम गुणांक...ऋणात्मक संख्यायही बात इसे अद्वितीय बनाती है।
कोर कोड:
python
coeffs = [0.483, 0.837, 0.224, -0.129]
# 处理第i个价格点
def smooth(prices, i):
weighted_sum = (prices[i] * 0.483 + # 当前价格
prices[i-1] * 0.837 + # 前1根,权重最大!
prices[i-2] * 0.224 + # 前2根
prices[i-3] * (-0.129)) # 前3根,负权重
weight_sum = 0.483 + 0.837 + 0.224 + (-0.129) # = 1.415
return weighted_sum / weight_sum
# 示例:smooth([100000, 101000, 99000, 102000], 3) ≈ 100251
**प्रमुख विशेषताऐं:**पिछली कैंडलस्टिक का भार (0.837) वर्तमान मूल्य (0.483) से अधिक है! इसका अर्थ है कि db4 "अभी घटित हुए मूल्य" पर अधिक जोर देता है, और नकारात्मक भार गुणांक पिछली कीमत पर "संतुलन" प्रभाव डालेगा, जिससे सुगमता और भी बढ़ जाएगी।
3. सिम्लेट 4 - एक सममितीय उन्नत संस्करण
सिम्लेट 4, बेहतर समरूपता के उद्देश्य से बनाया गया डाउबेचीज़ का उन्नत संस्करण है। गुणांक:[-0.076, -0.030, 0.498, 0.804, 0.298, -0.099, -0.013, 0.032]。
कोर कोड:
python
coeffs = [-0.076, -0.030, 0.498, 0.804, 0.298, -0.099, -0.013, 0.032]
# 向前看8根K线
def smooth(prices, i):
weighted_sum = sum(prices[i-j] * coeffs[j] for j in range(8))
weight_sum = sum(coeffs)
return weighted_sum / weight_sum
# 平滑效果比Haar和db4都强,但反应速度更慢
**प्रमुख विशेषताऐं:**आठ कैंडलस्टिक की विंडो लेंथ कीमतों की लंबी "मेमोरी" प्रदान करती है। एक चिकने वक्र पर वास्तविक ट्रेंड रिवर्सल आठ कैंडलस्टिक बीतने के बाद ही दिखाई दे सकता है।
4. बायोरथोगोनल 3.3 - पूर्ण समरूपता
बायोऑर्थोगोनल 3.3 (संक्षेप में bior3.3) एक पूर्णतः सममित तरंग है जिसके गुणांक इस प्रकार हैं:[-0.066, 0.283, 0.637, 0.283, -0.066]。
कोर कोड:
python
coeffs = [-0.066, 0.283, 0.637, 0.283, -0.066]
# ↑ 中心↑ ↑
# 完全对称的两端
# 处理中间价格点
def smooth(prices, i):
# 实际应用:只向前看,不使用未来数据
weighted_sum = (prices[i-4] * (-0.066) + # 前4根
prices[i-3] * 0.283 + # 前3根
prices[i-2] * 0.637 + # 前2根,权重最大
prices[i-1] * 0.283 + # 前1根
prices[i] * (-0.066)) # 当前
weight_sum = sum(coeffs) # = 1.071
return weighted_sum / weight_sum
**प्रमुख विशेषताऐं:**समरूपता यह सुनिश्चित करती है कि कोई "चरण विरूपण" न हो - चिकना वक्र अस्पष्ट रूप से बाईं या दाईं ओर नहीं खिसकेगा।
5. मैक्सिकन हैट - टर्निंग पॉइंट हंटर
मेक्सिकन हैट (जिसे रिकर वेवलेट भी कहा जाता है) गुणांक:[-0.1, 0.0, 0.4, 0.8, 0.4, 0.0, -0.1]इसका आकार मैक्सिकन सोम्ब्रेरो (टोपी) जैसा है।
कोर कोड:
python
coeffs = [-0.1, 0.0, 0.4, 0.8, 0.4, 0.0, -0.1]
# 负值 零 正值 最大 正值 零 负值
# ↓ ↓
# "惩罚"两端,增强拐点检测能力
def smooth(prices, i):
weighted_sum = (prices[i-6] * (-0.1) + # 左3,负权重
prices[i-5] * 0.0 + # 左2
prices[i-4] * 0.4 + # 左1
prices[i-3] * 0.8 + # 中心,权重最大
prices[i-2] * 0.4 + # 右1
prices[i-1] * 0.0 + # 右2
prices[i] * (-0.1)) # 右3,负权重
weight_sum = sum(coeffs)
return weighted_sum / weight_sum
**प्रमुख विशेषताऐं:**इसकी "बीच में चौड़ी और दोनों सिरों पर ऋणात्मक" संरचना इसे पता लगाने में विशेष रूप से सक्षम बनाती है।मोड़ बिंदु- वह महत्वपूर्ण क्षण जब कीमतें ऊपर की ओर रुझान से नीचे की ओर रुझान में बदल जाती हैं (या इसके विपरीत)। नकारात्मक भार गुणांक दूर की कीमतों को "दंडित" करता है, जिससे रुझान में बदलाव को तुरंत पकड़ा जा सकता है।
6. मोर्लेट - गॉसियन स्मूथिंग के बादशाह
मोर्लेट वेवलेट गॉसियन (सामान्य) वितरण पर आधारित है, जिसके गुणांक इस प्रकार हैं:[0.0625, 0.25, 0.375, 0.25, 0.0625]。
कोर कोड:
python
coeffs = [0.0625, 0.25, 0.375, 0.25, 0.0625]
# ↓ ↓ ↓中心 ↓ ↓
# 远端 近端 最高 近端 远端
# 完美的高斯钟形曲线
def smooth(prices, i):
weighted_sum = (prices[i-4] * 0.0625 + # 左2,6.25%
prices[i-3] * 0.25 + # 左1,25%
prices[i-2] * 0.375 + # 中心,37.5%
prices[i-1] * 0.25 + # 右1,25%
prices[i] * 0.0625) # 右2,6.25%
# 权重和正好 = 1.0,无需除法
return weighted_sum
**प्रमुख विशेषताऐं:**सभी वेवलेट्स में सबसे "सौम्य" होने के कारण, इसमें कोई नकारात्मक भार नहीं होता है, और सभी कीमतों को गणना में सहजता से शामिल किया जाता है। परिणामस्वरूप वक्र अत्यंत चिकना होता है, लेकिन इसकी कीमत धीमी प्रतिक्रिया है - कीमतों में अचानक परिवर्तन कई कैंडलस्टिक्स के बाद ही दिखाई दे सकते हैं।
7. डिस्क्रीट मेयर - अल्टीमेट स्मूथिंग
डिस्क्रीट मेयर वेवलेट सबसे जटिल वेवलेट है, जिसके गुणांक इस प्रकार हैं:[-0.015, -0.025, 0.0, 0.28, 0.52, 0.28, 0.0, -0.025, -0.015]。
कोर कोड:
python
coeffs = [-0.015, -0.025, 0.0, 0.28, 0.52, 0.28, 0.0, -0.025, -0.015]
# ↑ ↑ ↑ ↑中心↑ ↑ ↑ ↑
# 完全对称,中心权重超过50%
def smooth(prices, i):
# 向前看9根K线
weighted_sum = sum(prices[i-j] * coeffs[j] for j in range(9))
weight_sum = sum(coeffs) # = 1.0
return weighted_sum
# 注意:第4根之前的K线权重是0.52,超过50%!
# 实际上在告诉你"4根K线之前的中期趋势"
**प्रमुख विशेषताऐं:**इसमें सबसे अधिक गुणांक (9), सबसे लंबा ऐतिहासिक डेटा और सबसे मजबूत स्मूथिंग प्रभाव है। यह "साप्ताहिक रुझानों" को निकालने के लिए उपयुक्त है, लेकिन इसमें बहुत अधिक विलंब होता है - भले ही कीमत 10% गिर गई हो, इसका वक्र अभी भी "लगातार वृद्धि" दिखा सकता है।
5. स्मूथिंग प्रभाव में अंतर क्यों होते हैं?
सात प्रकार के वेवलेट्स की समीक्षा करने के बाद, आपको एक पैटर्न दिखाई देना चाहिए:
अधिक गुणांक = अधिक दृश्यता = बेहतर स्मूथिंग = अधिक विलंबता
हार (2 गुणांक) → केवल 1 बार देखें → लगभग चिकना नहीं
डाउबेचीज़ 4 (4 टुकड़े) → पहले 3 देखें → थोड़ा चिकना
मेक्सिकन टोपी (7) → इससे पहले 6 देखें → मध्यम स्मूथिंग
डिस्क्रीट मेयर (9) → 8 बार देखने से पहले → भारी स्मूथिंग
नकारात्मक भार का प्रभाव संवेदनशीलता को बढ़ाना और परिवर्तनों का पता लगाना आसान बनाना है।
हार/मोरलेट (कोई नकारात्मक भार नहीं) → कोमल और चिकना, असंवेदनशील
मेक्सिकन हैट (दोनों सिरों पर नकारात्मक) → परिवर्तन बिंदुओं के प्रति संवेदनशील
डाउबेचीज़ 4 (नकारात्मक) → प्रवृत्ति परिवर्तनों के प्रति संवेदनशील
समरूपता की भूमिका = कोई विकृति नहीं = मूल आकार को बनाए रखना
विषमता (डाउबेचीज़) → बाएँ/दाएँ खिसक सकती है
समरूपता (बायोऑर्थोगोनल/मेयर) → केंद्रीय स्थिति को बनाए रखना
VI. स्तरों को समतल करने का प्रभाव
वेवलेट ट्रांसफ़ॉर्म को एक के ऊपर एक रखी गुड़ियों की तरह पुनरावर्ती रूप से लागू किया जा सकता है। पहले अनुप्रयोग को लेवल 1 कहा जाता है, लेवल 1 के परिणाम पर इसे दोबारा लागू करने को लेवल 2 कहा जाता है, और इसी तरह आगे भी।
विभिन्न स्तरों पर देखी जाने वाली समय सीमाएँ:
मान लीजिए कि हम बीटीसी ट्रेडिंग के लिए 1-घंटे के कैंडलस्टिक चार्ट का उपयोग करते हैं:
स्तर 1 → 2-4 घंटों में होने वाले अल्पकालिक उतार-चढ़ावों का अवलोकन करें
स्तर 2 → 4-8 घंटों में रुझान का अवलोकन करें
स्तर 3 → 1-2 दिनों में मध्यम अवधि के रुझान का अवलोकन करें (आमतौर पर इस्तेमाल की जाने वाली रणनीति)
स्तर 4 → 2-4 दिनों की मूल्य सीमा का अवलोकन करें
स्तर 5 → 4-8 दिनों में प्रमुख रुझानों का अवलोकन करें
वास्तविक परिणामों की तुलना:
मूल बीटीसी मूल्य (1-घंटे का चार्ट):99500, 99800, 99200, 100200, 99800, 100500, 100100, ...
लेवल 1 प्रोसेसिंग: 99600, 99650, 99500, 99900, 99950, 100200, 100250, ...
(थोड़ा समतल किया गया है, लेकिन उतार-चढ़ाव अभी भी दिखाई दे रहे हैं)
लेवल 3 प्रोसेसिंग: 99620, 99650, 99700, 99800, 99950, 100100, 100200, ...
(सरलीकृत किया गया, जो मध्यम अवधि के रुझान को दर्शाता है)
लेवल 5 प्रोसेसिंग: 99630, 99640, 99660, 99700, 99760, 99840, 99930, ...
(बेहद सहज, केवल सामान्य दिशा दर्शा रहा है)
चयन का सिद्धांत सरल है: अपनी होल्डिंग अवधि के आधार पर संबंधित स्तर का उपयोग करें।
15 मिनट की स्कैल्पिंग → स्तर 1-2
इंट्राडे ट्रेडिंग → स्तर 2-3
कुछ दिनों तक स्विंग डांस करें → लेवल 3-4
दीर्घकालिक प्रवृत्ति विश्लेषण → स्तर 4-5
VII. व्यावहारिक अनुप्रयोग के विचार
ट्रेडिंग में वेवलेट ट्रांसफॉर्म का उपयोग बहुत सीधा है: इससे उत्पन्न स्मूथेड प्राइस कर्व का उपयोग करके ट्रेंड की दिशा निर्धारित करें और ट्रेंड बदलने पर ट्रेड करें। विशेष रूप से, यदि स्मूथेड क्लोजिंग प्राइस पिछले क्लोजिंग प्राइस से अधिक है, तो यह ऊपर की ओर ट्रेंड का संकेत देता है, इसलिए लॉन्ग पोजीशन लें; यदि स्मूथेड क्लोजिंग प्राइस पिछले क्लोजिंग प्राइस से कम है, तो यह नीचे की ओर ट्रेंड का संकेत देता है, इसलिए पोजीशन बंद करें या शॉर्ट पोजीशन लें। यह तर्क प्रभावी है क्योंकि वेवलेट्स ने अल्पकालिक यादृच्छिक उतार-चढ़ाव को फ़िल्टर कर दिया है, जिससे "ऊपर" या "नीचे" की स्थिति शोर के कारण उत्पन्न गलत संकेत के बजाय वास्तविक ट्रेंड परिवर्तन की उच्च संभावना के रूप में रह जाती है।
python
# 执行小波变换
transformed = transformer.transform_ohlc(df)
# 获取最近两根K线的平滑收盘价
w_close_current = transformed['w_close'].values[-1] # 当前平滑收盘价
w_close_prev = transformed['w_close'].values[-2] # 前一根平滑收盘价
# 判断趋势方向
signal = 0
if w_close_current > w_close_prev:
signal = 1 # 平滑价格向上 → 做多
elif w_close_current < w_close_prev:
signal = -1 # 平滑价格向下 → 做空
# 获取账户信息
account = exchange.GetAccount()
ticker = exchange.GetTicker()
if not account or not ticker:
Log("[Warning] Failed to get account/ticker info")
Sleep(5000)
continue
current_price = ticker['Last']
Log(f"[Price] 原始: {df['Close'].values[-1]:.2f}, "
f"平滑当前: {w_close_current:.2f}, 平滑前值: {w_close_prev:.2f}")
Log(f"[Trend] {'↑ 向上' if signal == 1 else '↓ 向下' if signal == -1 else '→ 横盘'}")
# 执行交易逻辑
if signal == 1 and position != 1:
# 平滑价格向上 → 做多
Log(f"[信号] 趋势向上,开多 @ {current_price:.2f}")
if position == -1:
# 先平空仓
exchange.SetDirection("closesell")
exchange.Buy(current_price, 1)
Log(f"[平仓] 平空仓")
# 开多仓
exchange.SetDirection("buy")
exchange.Buy(current_price, 1)
Log(f"[开仓] 开多仓")
position = 1
elif signal == -1 and position != -1:
# 平滑价格向下 → 做空
Log(f"[信号] 趋势向下,开空 @ {current_price:.2f}")
if position == 1:
# 先平多仓
exchange.SetDirection("closebuy")
exchange.Sell(current_price, 1)
Log(f"[平仓] 平多仓")
# 开空仓
exchange.SetDirection("sell")
exchange.Sell(current_price, 1)
Log(f"[开仓] 开空仓")
position = -1
else:
Log(f"[持仓] 当前{'多头' if position == 1 else '空头' if position == -1 else '空仓'},无需操作")
बेशक, व्यवहार में यह इतना आसान नहीं है। आप एक साथ कई वेवलेट स्तरों का उपयोग कर सकते हैं, जैसे कि स्तर 2 अल्पकालिक प्रवृत्ति को दर्शाता है और स्तर 4 दीर्घकालिक प्रवृत्ति को। पोजीशन तभी खोलें जब दोनों एक ही दिशा में आगे बढ़ रहे हों, जिससे गलत संकेतों की संभावना काफी कम हो जाती है। आप अन्य फ़िल्टरिंग शर्तें भी जोड़ सकते हैं, जैसे कि ट्रेडिंग वॉल्यूम बढ़ाना, पर्याप्त उच्च अस्थिरता या किसी महत्वपूर्ण स्तर से ऊपर मूल्य का ब्रेकआउट होना; ये सभी जीत दर को बेहतर बना सकते हैं। स्टॉप-लॉस ऑर्डर के लिए, आप वेवलेट-स्मूथेड मूल्य उतार-चढ़ाव सीमा का उपयोग करके उन्हें गतिशील रूप से सेट कर सकते हैं; उदाहरण के लिए, स्टॉप-लॉस तब लागू होगा जब मूल्य स्मूथेड मूल्य माइनस 2 गुना एटीआर से नीचे गिर जाए। पोजीशन प्रबंधन में, प्रवृत्ति जितनी स्पष्ट होगी (स्मूथेड मूल्य का ढलान जितना तीव्र होगा), पोजीशन का आकार उतना ही बड़ा होगा; यदि प्रवृत्ति स्पष्ट नहीं है, तो छोटी पोजीशन लें या कुछ समय के लिए ट्रेडिंग न करें।
लेकिन मूल विचार वही रहता है: शोरगुल वाले मूल्यों को स्पष्ट रुझानों में बदलने के लिए वेवलेट्स का उपयोग करें, और फिर उन स्पष्ट रुझानों के आधार पर निर्णय लें। यह मूल कैंडलस्टिक चार्ट पर उतार-चढ़ाव को सीधे देखने की तुलना में कहीं अधिक विश्वसनीय है, क्योंकि मूल कैंडलस्टिक चार्ट आज 3% बढ़ सकता है, कल 2% गिर सकता है और परसों 4% बढ़ सकता है। आप यह अंतर नहीं कर सकते कि यह एक रुझान है या उतार-चढ़ाव। वेवलेट्स द्वारा संसाधित वक्र आपको बताएगा कि "इस अवधि के दौरान समग्र रुझान ऊपर की ओर है, हालांकि बीच-बीच में उतार-चढ़ाव होते हैं"।
VIII. निष्कर्ष: "त्रिस्तरीय दृष्टिकोण" का एक तर्कसंगत परिप्रेक्ष्य
व्यावहारिक रूप से डेटा को सुचारू बनाने के संदर्भ में, वेवलेट ट्रांसफ़ॉर्म वास्तव में वित्तीय डेटा प्रोसेसिंग में महत्वपूर्ण भूमिका निभा सकता है: यह कुछ अल्पकालिक शोर को फ़िल्टर कर सकता है और अपेक्षाकृत स्पष्ट प्रवृत्ति संबंधी जानकारी निकालने में मदद कर सकता है। हालाँकि, इस तकनीक की कुछ महत्वपूर्ण सीमाएँ भी हैं।**लैग की समस्या को पूरी तरह से टाला नहीं जा सकता।**हालांकि, यह केवल ऐतिहासिक डेटा को ही संसाधित कर सकता है और भविष्य के रुझानों की भविष्यवाणी नहीं कर सकता। इसके अलावा, अकेले वेवलेट ट्रांसफॉर्म का प्रभाव अपेक्षाकृत सीमित है; एक संपूर्ण ट्रेडिंग सिस्टम बनाने के लिए इसे अन्य विश्लेषणात्मक विधियों और जोखिम नियंत्रण उपायों के साथ संयोजित करने की आवश्यकता है।
इस सीमा का मूल कारण वित्तीय बाजारों की अनूठी प्रकृति है। वाक् पहचान और छवि प्रसंस्करण जैसे पारंपरिक सिग्नल प्रोसेसिंग क्षेत्रों में, शोर की विशेषताएं अपेक्षाकृत स्थिर होती हैं और सिग्नल पैटर्न दोहराए जाते हैं। इसलिए, वेवलेट ट्रांसफॉर्म संकेतों को शोर से प्रभावी ढंग से अलग कर सकता है। हालांकि, वित्तीय बाजार पूरी तरह से अलग हैं: आज "शोर" माने जाने वाले उतार-चढ़ाव कल बाजार परिवर्तनों को दर्शाने वाले "संकेत" बन सकते हैं; जो विश्लेषणात्मक मॉडल आज प्रभावी हैं, वे भविष्य में अप्रभावी हो सकते हैं।**बाजार स्वयं स्थिर नहीं है और गतिशील रूप से बदलता रहता है।**वेवलेट ट्रांसफॉर्म में कोई अपरिवर्तनीय नियम नहीं हैं, जिसके लिए वित्तीय क्षेत्र में वेवलेट ट्रांसफॉर्म के अनुप्रयोग को विशिष्ट बाजार परिवेश के अनुसार लचीले ढंग से समायोजित करने की आवश्यकता होती है।
जब आप किसी को वेवलेट ट्रांसफॉर्म और फोरियर ट्रांसफॉर्म के वास्तविक प्रभावों को बढ़ा-चढ़ाकर बताते हुए देखें, तो ये प्रश्न पूछने का प्रयास करें: किस प्रकार के वेवलेट का उपयोग किया गया था? अन्य प्रकारों के बजाय इस प्रकार को चुनने का आधार क्या है? स्मूथिंग स्तर कैसे निर्धारित किया गया था? क्या इससे संबंधित बैकटेस्टिंग परिणाम और पैरामीटर चयन प्रक्रियाएं उपलब्ध हैं?जिनके पास वास्तव में पेशेवर ज्ञान है, वे इन प्रमुख तकनीकी विवरणों को स्पष्ट रूप से समझा सकेंगे।
अपने सीमित ज्ञान के आधार पर, हमने यह व्यावहारिक अन्वेषण किया।**इसका मूल उद्देश्य वेवलेट ट्रांसफॉर्म के अनुप्रयोग संबंधी अवधारणाओं को सरल और आसानी से समझने योग्य तरीके से साझा करना है।**इस लेख का उद्देश्य पाठकों को इस तकनीक की बुनियादी समझ प्रदान करना है। हम इस क्षेत्र में गहनता से कार्यरत मात्रात्मक शोधकर्ताओं का बहुत सम्मान करते हैं; यदि आप इस क्षेत्र के विशेषज्ञ हैं, तो आपसे निवेदन है कि लेख में किसी भी कमी को इंगित करें—जैसे कि वेवलेट पैरामीटर चयन का सैद्धांतिक आधार, बहु-स्तरीय संयोजनों के लिए अनुकूलन विधियाँ, और अनुकूली वेवलेट चयन के कार्यान्वयन पथ। हम आपके सुझावों का सहर्ष स्वागत करेंगे और सामग्री में निरंतर सुधार करते रहेंगे।
प्लॉटिंग फ़ंक्शन: आविष्कारक के स्थानीय बैकटेस्टिंग इंजन में लागू किया गया
python
'''backtest
start: 2025-12-17 00:00:00
end: 2025-12-23 08:00:00
period: 1h
basePeriod: 1h
exchanges: [{"eid":"Futures_Binance","currency":"BTC_USDT","fee":[0,0]}]
'''
from fmz import *
import numpy as np
import pandas as pd
import matplotlib.pyplot as plt
from matplotlib.patches import Rectangle
task = VCtx(__doc__)
# ==================== 小波系数库 ====================
class WaveletCoefficients:
"""Wavelet Coefficients Definition"""
@staticmethod
def get_coeffs(wavelet_name):
"""Get coefficients for different wavelet types"""
coeffs = {
"Haar": [0.5, 0.5],
"Daubechies 4": [
0.48296291314453414,
0.8365163037378079,
0.22414386804201339,
-0.12940952255126037
],
"Symlet 4": [
-0.05357, -0.02096, 0.35238,
0.56833, 0.21062, -0.07007,
-0.01941, 0.03268
],
"Biorthogonal 3.3": [
-0.06629, 0.28289, 0.63678,
0.28289, -0.06629
],
"Mexican Hat (Ricker)": [
-0.1, 0.0, 0.4, 0.8, 0.4, 0.0, -0.1
],
"Morlet (Gaussian)": [
0.0625, 0.25, 0.375, 0.25, 0.0625
],
"Discrete Meyer (Dmey)": [
-0.015, -0.025, 0.0,
0.28, 0.52, 0.28,
0.0, -0.025, -0.015
]
}
return coeffs.get(wavelet_name, coeffs["Mexican Hat (Ricker)"])
# ==================== 小波变换引擎 ====================
class WaveletTransform:
"""Wavelet Transform Engine"""
def __init__(self, wavelet_type="Mexican Hat (Ricker)", smoothing_level=3):
self.wavelet_type = wavelet_type
self.smoothing_level = smoothing_level
self.coeffs = WaveletCoefficients.get_coeffs(wavelet_type)
def convolve(self, src, coeffs, step):
"""
Convolution operation - Core algorithm
Args:
src: Source data sequence
coeffs: Wavelet coefficients
step: Sampling step
Returns:
Convolved value
"""
sum_val = 0.0
sum_w = 0.0
for i, weight in enumerate(coeffs):
idx = i * step
if idx < len(src):
val = src[idx]
sum_val += val * weight
sum_w += weight
# Normalization - Critical fix
return sum_val / sum_w if sum_w != 0 else sum_val
def calc_level(self, data, target_level):
"""
Calculate wavelet transform for specified level
Args:
data: Original data array
target_level: Target smoothing level
Returns:
Transformed data array
"""
result = []
coeffs = self.coeffs
for i in range(len(data)):
# Get data from current position backwards
src = data[max(0, i - 50):i + 1][::-1]
# Level 1
val = self.convolve(src, coeffs, 1)
# Level 2
if target_level >= 2:
src_temp = [val] + [self.convolve(data[max(0, j - 50):j + 1][::-1], coeffs, 1)
for j in range(max(0, i - 10), i)][::-1]
val = self.convolve(src_temp, coeffs, 2)
# Level 3
if target_level >= 3:
val = self.convolve([val] * len(coeffs), coeffs, 4)
# Level 4+
if target_level >= 4:
val = self.convolve([val] * len(coeffs), coeffs, 8)
result.append(val)
return np.array(result)
def transform_ohlc(self, df):
"""
Perform wavelet transform on OHLC data
Args:
df: DataFrame with Open/High/Low/Close
Returns:
Transformed DataFrame
"""
result_df = df.copy()
# Transform each price series
result_df['w_open'] = self.calc_level(df['Open'].values, self.smoothing_level)
result_df['w_high'] = self.calc_level(df['High'].values, self.smoothing_level)
result_df['w_low'] = self.calc_level(df['Low'].values, self.smoothing_level)
result_df['w_close'] = self.calc_level(df['Close'].values, self.smoothing_level)
# Reconstruct logically consistent candlesticks
result_df['real_high'] = result_df[['w_high', 'w_low', 'w_open', 'w_close']].max(axis=1)
result_df['real_low'] = result_df[['w_high', 'w_low', 'w_open', 'w_close']].min(axis=1)
return result_df
# ==================== K线图可视化工具 ====================
class WaveletCandlestickVisualizer:
"""Wavelet Candlestick Visualization"""
@staticmethod
def plot_single_wavelet(df, wavelet_type, smoothing_level=3, n_bars=200):
"""
Plot single wavelet type comparison
Args:
df: Original candlestick data
wavelet_type: Wavelet type
smoothing_level: Smoothing level
n_bars: Number of bars to display
"""
# Take only last n_bars
df_plot = df.iloc[-n_bars:].copy()
# Create figure
fig, ax = plt.subplots(figsize=(20, 8))
# Perform wavelet transform
transformer = WaveletTransform(wavelet_type, smoothing_level)
transformed = transformer.transform_ohlc(df)
transformed_plot = transformed.iloc[-n_bars:].copy()
# Draw original candlesticks (gray background)
WaveletCandlestickVisualizer._draw_candlesticks(
ax, df_plot,
color_up='lightgray',
color_down='lightgray',
alpha=0.3,
label='Original Candles'
)
# Draw wavelet smoothed candlesticks
WaveletCandlestickVisualizer._draw_candlesticks(
ax, transformed_plot,
use_wavelet=True,
color_up='#26A69A', # Green
color_down='#EF5350', # Red
alpha=0.9,
linewidth=1.2,
label=f'{wavelet_type} Smoothed (Level {smoothing_level})'
)
# Set title and labels
ax.set_title(f'{wavelet_type} Wavelet (Level {smoothing_level}) - Candlestick Comparison',
fontsize=16, fontweight='bold', pad=20)
ax.set_ylabel('Price (USDT)', fontsize=13)
ax.set_xlabel('Time', fontsize=13)
ax.grid(True, alpha=0.2, linestyle='--')
ax.legend(loc='upper left', fontsize=12)
# Format x-axis
ax.set_xlim(-1, len(df_plot))
ax.set_xticks(range(0, len(df_plot), max(1, len(df_plot) // 10)))
ax.set_xticklabels([df_plot.index[i].strftime('%m-%d %H:%M')
for i in range(0, len(df_plot), max(1, len(df_plot) // 10))],
rotation=45, ha='right')
plt.tight_layout()
plt.show()
return fig
@staticmethod
def plot_single_level(df, wavelet_type, level, n_bars=200):
"""
Plot single smoothing level
Args:
df: Original candlestick data
wavelet_type: Wavelet type
level: Smoothing level
n_bars: Number of bars to display
"""
# Take only last n_bars
df_plot = df.iloc[-n_bars:].copy()
# Create figure
fig, ax = plt.subplots(figsize=(20, 8))
# Perform wavelet transform
transformer = WaveletTransform(wavelet_type, level)
transformed = transformer.transform_ohlc(df)
transformed_plot = transformed.iloc[-n_bars:].copy()
# Draw original candlesticks
WaveletCandlestickVisualizer._draw_candlesticks(
ax, df_plot,
color_up='lightgray',
color_down='lightgray',
alpha=0.3,
label='Original Candles'
)
# Draw wavelet smoothed candlesticks
WaveletCandlestickVisualizer._draw_candlesticks(
ax, transformed_plot,
use_wavelet=True,
color_up='#26A69A',
color_down='#EF5350',
alpha=0.9,
linewidth=1.2,
label=f'Level {level} Smoothed'
)
# Set title and labels
ax.set_title(f'{wavelet_type} - Smoothing Level {level} Effect',
fontsize=16, fontweight='bold', pad=20)
ax.set_ylabel('Price (USDT)', fontsize=13)
ax.set_xlabel('Time', fontsize=13)
ax.grid(True, alpha=0.2, linestyle='--')
ax.legend(loc='upper left', fontsize=12)
# Format x-axis
ax.set_xlim(-1, len(df_plot))
ax.set_xticks(range(0, len(df_plot), max(1, len(df_plot) // 10)))
ax.set_xticklabels([df_plot.index[i].strftime('%m-%d %H:%M')
for i in range(0, len(df_plot), max(1, len(df_plot) // 10))],
rotation=45, ha='right')
plt.tight_layout()
plt.show()
return fig
@staticmethod
def _draw_candlesticks(ax, df, use_wavelet=False, color_up='green',
color_down='red', alpha=1.0, linewidth=1.0, label=''):
"""
Draw candlestick chart
Args:
ax: Matplotlib axis
df: Data DataFrame
use_wavelet: Whether to use wavelet data
color_up: Up color
color_down: Down color
alpha: Transparency
linewidth: Line width
label: Legend label
"""
if use_wavelet:
opens = df['w_open'].values
highs = df['real_high'].values
lows = df['real_low'].values
closes = df['w_close'].values
else:
opens = df['Open'].values
highs = df['High'].values
lows = df['Low'].values
closes = df['Close'].values
for i in range(len(df)):
x = i
open_price = opens[i]
high_price = highs[i]
low_price = lows[i]
close_price = closes[i]
color = color_up if close_price >= open_price else color_down
# Draw wick
ax.plot([x, x], [low_price, high_price],
color=color, linewidth=linewidth, alpha=alpha)
# Draw body
height = abs(close_price - open_price)
bottom = min(open_price, close_price)
rect = Rectangle((x - 0.3, bottom), 0.6, height,
facecolor=color, edgecolor=color,
alpha=alpha, linewidth=linewidth)
ax.add_patch(rect)
# Add legend (only once)
if label:
ax.plot([], [], color=color_up, linewidth=3, alpha=alpha, label=label)
# ==================== 主函数 ====================
def main():
"""Main execution flow"""
exchange.SetCurrency("BTC_USDT")
exchange.SetContractType("swap")
# Get candlestick data
records = exchange.GetRecords(PERIOD_H1, 500)
# Convert to DataFrame
df = pd.DataFrame(records, columns=['Time', 'Open', 'High', 'Low', 'Close', 'Volume'])
df['Time'] = pd.to_datetime(df['Time'], unit='ms')
df.set_index('Time', inplace=True)
print(f"Data loaded: {len(df)} bars")
print(f"Time range: {df.index[0]} to {df.index[-1]}")
print(f"Price range: ${df['Low'].min():.2f} - ${df['High'].max():.2f}")
return df
# ==================== 执行绘图 ====================
try:
# Get candlestick data
kline = main()
print("\n" + "="*70)
print("Generating Wavelet Candlestick Charts (Each in Separate Window)...")
print("="*70)
# ========== Chart Series 1: Different Wavelet Types ==========
print("\n[Series 1] Comparing Different Wavelet Types")
print("-" * 70)
wavelet_types = [
"Haar",
"Daubechies 4",
"Symlet 4",
"Biorthogonal 3.3",
"Mexican Hat (Ricker)",
"Morlet (Gaussian)",
"Discrete Meyer (Dmey)" # ✅ 添加了 Discrete Meyer
]
for i, wavelet_type in enumerate(wavelet_types, 1):
print(f" Chart {i}/{len(wavelet_types)}: {wavelet_type}")
fig = WaveletCandlestickVisualizer.plot_single_wavelet(
kline,
wavelet_type=wavelet_type,
smoothing_level=3,
n_bars=150
)
# ========== Chart Series 2: Different Smoothing Levels ==========
print("\n[Series 2] Comparing Different Smoothing Levels")
print("-" * 70)
levels = [1, 2, 3, 4, 5]
for i, level in enumerate(levels, 1):
print(f" Chart {i}/5: Level {level}")
fig = WaveletCandlestickVisualizer.plot_single_level(
kline,
wavelet_type="Mexican Hat (Ricker)",
level=level,
n_bars=150
)
print("\n" + "="*70)
print("All charts generated successfully!")
print(f"Total charts: {len(wavelet_types) + len(levels)} ({len(wavelet_types)} wavelets + {len(levels)} levels)")
print("="*70)
except Exception as e:
print(f"Error: {str(e)}")
import traceback
print(traceback.format_exc())
finally:
print("\nStrategy testing completed.")
लेनदेन संबंधी कार्य: इन्वेंटर्स प्लेटफॉर्म पर लागू
python
'''backtest
start: 2025-01-17 00:00:00
end: 2025-12-23 08:00:00
period: 1h
basePeriod: 1h
exchanges: [{"eid":"Futures_Binance","currency":"BTC_USDT","fee":[0,0]}]
'''
import numpy as np
import pandas as pd
# ==================== 小波系数库 ====================
class WaveletCoefficients:
"""与上部分函数一致"""
# ==================== 小波变换引擎 ====================
class WaveletTransform:
"""与上部分函数一致"""
def main():
"""小波交易主函数 - 基于平滑价格趋势"""
# ========== 配置参数 ==========
WAVELET_TYPE = "Mexican Hat (Ricker)" # 小波类型
SMOOTHING_LEVEL = 1 # 平滑阶数
# 初始化
exchange.SetCurrency("BTC_USDT")
exchange.SetContractType("swap")
Log(f"=" * 70)
Log(f"Wavelet Trend Following Strategy")
Log(f"Wavelet: {WAVELET_TYPE}, Level: {SMOOTHING_LEVEL}")
Log(f"Logic: 平滑收盘价向上→做多, 平滑收盘价向下→做空")
Log(f"=" * 70)
# 初始化小波变换器
transformer = WaveletTransform(WAVELET_TYPE, SMOOTHING_LEVEL)
# 持仓状态
position = 0 # 0: 无持仓, 1: 多头, -1: 空头
while True:
# 获取K线数据
records = exchange.GetRecords(PERIOD_H1, 500)
if not records:
Log("[Warning] Failed to get kline data")
Sleep(5000)
continue
df = pd.DataFrame(records, columns=['Time', 'Open', 'High', 'Low', 'Close', 'Volume'])
df['Time'] = pd.to_datetime(df['Time'], unit='ms')
df.set_index('Time', inplace=True)
# 执行小波变换
transformed = transformer.transform_ohlc(df)
# 获取最近两根K线的平滑收盘价
w_close_current = transformed['w_close'].values[-1] # 当前平滑收盘价
w_close_prev = transformed['w_close'].values[-2] # 前一根平滑收盘价
# 判断趋势方向
signal = 0
if w_close_current > w_close_prev:
signal = 1 # 平滑价格向上 → 做多
elif w_close_current < w_close_prev:
signal = -1 # 平滑价格向下 → 做空
# 获取账户信息
account = exchange.GetAccount()
ticker = exchange.GetTicker()
if not account or not ticker:
Log("[Warning] Failed to get account/ticker info")
Sleep(5000)
continue
current_price = ticker['Last']
Log(f"[Price] 原始: {df['Close'].values[-1]:.2f}, "
f"平滑当前: {w_close_current:.2f}, 平滑前值: {w_close_prev:.2f}")
Log(f"[Trend] {'↑ 向上' if signal == 1 else '↓ 向下' if signal == -1 else '→ 横盘'}")
# 执行交易逻辑
if signal == 1 and position != 1:
# 平滑价格向上 → 做多
Log(f"[信号] 趋势向上,开多 @ {current_price:.2f}")
if position == -1:
# 先平空仓
exchange.SetDirection("closesell")
exchange.Buy(current_price, 1)
Log(f"[平仓] 平空仓")
# 开多仓
exchange.SetDirection("buy")
exchange.Buy(current_price, 1)
Log(f"[开仓] 开多仓")
position = 1
elif signal == -1 and position != -1:
# 平滑价格向下 → 做空
Log(f"[信号] 趋势向下,开空 @ {current_price:.2f}")
if position == 1:
# 先平多仓
exchange.SetDirection("closebuy")
exchange.Sell(current_price, 1)
Log(f"[平仓] 平多仓")
# 开空仓
exchange.SetDirection("sell")
exchange.Sell(current_price, 1)
Log(f"[开仓] 开空仓")
position = -1
else:
Log(f"[持仓] 当前{'多头' if position == 1 else '空头' if position == -1 else '空仓'},无需操作")
Log(f"[账户] 余额: {account['Balance']:.2f}, 权益: {account['Equity']:.2f}")
Log("-" * 70)
Sleep(60000 * 60)
- 1













