
सभी को नमस्कार!
मैं तीसरे वर्ष का छात्र हूं, और विश्वविद्यालय में अपनी पढ़ाई की शुरुआत में मैंने
रूसी एई कप , और बाद में
मिनी ऐ कप के बारे में सीखा, कृत्रिम बुद्धिमत्ता में प्रतियोगिताओं, और अच्छे परिणाम दिखाते हुए सक्रिय रूप से उनमें भाग लेना शुरू किया। इस बार, RAIC सत्र में सीधे गिर गया, इसलिए कुछ भी मुझे रोक नहीं सका :) और आज मैं आपको बताना चाहता हूं कि मैं दूसरा स्थान लेने में कैसे कामयाब रहा।
प्रतियोगिता के नियम प्रतियोगिता वेबसाइट पर और साथ ही इस
लेख में पाए जा सकते हैं। मेरी प्रोफ़ाइल से लिंक करें:
Russianaicup.ru/profile/TonyKएक ओर, इस वर्ष का कार्य पिछले वर्षों के कार्यों के समान था, और ऐसा लगता था कि वैचारिक समाधान पिछले वाले (एगर आईओ और मैड कार) के समान होगा; लगभग एक सप्ताह के बाद मैं ऊब जाएगा और भाग लेने से थक गया।
दूसरी ओर, मैं समझ गया कि मैंने भौतिकी के साथ पिछली प्रतियोगिताओं में बहुत कुछ सीखा है और अब मैं इस अनुभव को लागू कर सकता हूं, पुरानी रेक पर कदम नहीं और अंत में, बेहतर परिणाम दिखा सकता हूं।
विज़ुअलाइज़ेशन के लिए, मैंने तय किया कि मेरे पास अलग-अलग अक्षों पर पर्याप्त अनुमान होगा, या एक निश्चित कोण पर प्रदर्शित होगा। लेकिन मैं बहुत गलत था, और अगर यह स्थानीय धावक में बनाए गए जादू विज़ुअलाइज़र के लिए नहीं था, जो आयोजकों ने बाद में जोड़ा, मुझे उन 3 डी विज़ुअलाइज़र को उधार लेना होगा, जिन्होंने बीटा परीक्षण चरण लिखने में खर्च किए और उन्हें सार्वजनिक डोमेन में डाल दिया।
इस बार सिम्युलेटर का छद्म कोड उपलब्ध था, जो उन लोगों की संभावनाओं को समान करता था, जो भौतिक विज्ञान को उल्टा करना जानते थे और एक शांत बॉट लिखना जानते थे, और जो लोग रिवर्स भौतिकी नहीं कर सकते थे, लेकिन जो एक मजबूत बॉट भी लिख सकते थे। मुझे लगता है कि आयोजकों द्वारा यह एक अच्छा निर्णय था।
मैंने जो पहली चीज़ की थी, वह C ++ में प्रलेखन से सिम्युलेटर कोड को फिर से लिखना था, और फिर अपने पुराने कंप्यूटर और सर्वर पर सिम्युलेटर के समय को मापा। दूसरे मामले में, यह दो बार तेजी से निकला, हालांकि यह उम्मीद की गई थी। मुझे लगा कि कितनी बार और कितनी गहराई तक मैं अनुकरण कर सकता हूं। यह तुरंत स्पष्ट हो गया कि किसी को 100 माइक्रोटिक्स के ईमानदार सिमुलेशन के बारे में भूलना होगा (सर्वर पर भौतिकी के एक टिक को 100 "माइक्रोटिक्स" में विभाजित किया गया था), और यह राउंडअबाउट तरीकों से सटीकता के साथ समस्याओं को हल करने के लिए आवश्यक होगा।
इस तथ्य के कारण कि शेल को इस तरह से व्यवस्थित किया गया था कि प्रत्येक रोबोट के लिए कार्रवाई अनुरोध को प्रत्येक टिक पर अलग-अलग कहा जाता है, मैंने एक साधारण तर्क को लागू किया: उस समय जब पहला रोबोट एक कार्रवाई के लिए कहा जाता है, कार्यक्रम सभी रोबोटों को याद करता है और याद दिलाता है पहले की कार्रवाई, और जब बाकी रोबोटों से कार्रवाई पूछी जाती है, तो वह वापस वही देता है जो उसे याद था।
मैं बॉट को जल्द ही युद्ध में भेजने के लिए अधीर था। मैंने यादृच्छिक प्रक्षेपवक्र उत्पन्न करने और सर्वश्रेष्ठ चुनने का फैसला किया। उसी समय, वह उत्पन्न सेट को कुछ जटिल कार्यों को करना संभव बनाता था, उदाहरण के लिए, दाईं ओर से गेंद के चारों ओर जाना, और फिर हिट करना।
प्रक्षेपवक्र एक कार्य योजना है। प्रारंभ में, प्रक्षेपवक्र यह था:
- एक यादृच्छिक कोण पर कार्रवाई सेट करें;
- प्रक्षेपवक्र के एक यादृच्छिक टिक पर, कोण को दूसरे यादृच्छिक एक में बदलें;
- प्रक्षेपवक्र के एक यादृच्छिक टिक में एक बार कूदो।
प्रक्षेपवक्रों का ऐसा स्थान यादृच्छिक खोजों के लिए एक अच्छा फिट था, जो दस्तावेज़ों से कच्चे सिम्युलेटर के साथ मैं (और, शायद, उस समय हर कोई) कर सकता था। अच्छा प्रक्षेपवक्र अक्सर अनुमान लगाया जाता था, और चूंकि पिछले टिक से सबसे अच्छा प्रक्षेपवक्र संरक्षित किया गया था, इसलिए खोज समय में फैल गई।
सभी वस्तुओं को सिम्युलेटर में रखा गया था: मेरे रोबोट, प्रतिद्वंद्वी के रोबोट और गेंद। मूल्यांकन सबसे सरल था: गेंद से दुश्मन के गोल की दूरी का योग और किसी के लिए लक्ष्य के लिए प्रक्षेपवक्र और बड़े मूल्यों के सभी बिंदुओं पर। सिमुलेशन गहराई 200 टिक। दुश्मनों की भविष्यवाणी उनकी अंतिम गति से की जाती है।

मैंने तुरंत दूसरे रोबोट के लिए एक अलग कार्रवाई जोड़ दी, साथ ही कूद को रद्द करने के लिए मजबूर किया, अगर उड़ान के दौरान गेंद के साथ कोई संपर्क नहीं था, इसलिए व्यर्थ में कूदने के लिए नहीं। उसी समय, मेरे रोबोट आधे से अधिक हो गए और एक दूसरे के सर्वश्रेष्ठ प्रक्षेपवक्र को जानते थे। अब मजबूत विरोधियों के लिए पहला
लक्ष्य शुरू हो गया है, जिनके पास पहले से ही गोलकीपर और कुछ अधिक जटिल तर्क थे।
यह आगे पता चला कि मैंने दुश्मन के फाटकों के लिए दूरी पर विचार नहीं किया, लेकिन क्षेत्र के केंद्र के किनारे (
x
और
z
मिलाया), लेकिन इससे किसी भी तरह से रणनीति को प्रभावित नहीं किया गया। यह अच्छा है कि सुधार के बाद यह खराब नहीं हुआ। ऐसा अक्सर तब होता है जब आप बॉट लिखते हैं।
फिर उन्होंने स्कोर को बदलकर गोलकीपर को जोड़ा: उन्होंने मेरे आधे क्षेत्र में गेंद के लिए और मेरे लिए गोल करने के लिए जुर्माना लगाया, और गोलकीपर से मेरे लक्ष्य की दूरी का भी अनुमान लगाया। अब गोलकीपर लक्ष्य पर खड़ा था और गेंद को नॉक आउट कर दिया। एक महत्वपूर्ण अनुकूलन यह था कि यदि गेंद मेरे आधे क्षेत्र में नहीं है, तो 90% समय हमलावर को और 10% गोलकीपर को दिया जाता है, अन्यथा 50%।
प्रत्येक बिंदु पर रोबोट के प्रक्षेपवक्र का आकलन 0.9 ^ की गहराई से गुणा किया गया था, मैंने इस गुणांक को पूरे स्कोरिंग की तरह अनुभवजन्य रूप से प्राप्त किया। "यह काम करता है, ठीक है" के सिद्धांत पर गुणांक के मान बहुत लंबे समय तक नहीं बदले।
उसने शीर्ष
पर जीत हासिल करना शुरू
किया और रैंकिंग में तेजी से वृद्धि हुई। बीटा चरण समाप्त हो गया है।
लंबे समय तक मेरे पास रणनीति पर कोई विचार नहीं था, संस्करण मामूली संपादन के लिए उल्लेखनीय थे, बग फिक्स (यह पता चला कि मैंने औसत रिबाउंड की ताकत को माना है
(MAX_HIT_E - MIN_HIT_E) / 2
), और सिम्युलेटर को भी अनुकूलित किया है। प्रक्षेपवक्रों की संख्या के द्वारा एक महत्वपूर्ण भूमिका निभाई गई थी जिसे मैं प्रति टिक के अनुसार हल करने में कामयाब रहा, इसलिए मैंने अनुकूलन पर ध्यान केंद्रित किया। हटाए गए साइनस और वर्गमूल। कोण बदलने से पहले या बाद में प्रक्षेपवक्र पर एक अप्रत्याशित शून्य गति जोड़ा गया। थोड़ा बदल स्कोरिंग।
16 वां संस्करण लंबे समय तक तालिका के शीर्ष पर
रखा गया था, लेकिन बीटा परीक्षण की समाप्ति के एक सप्ताह बाद, जैसा कि अपेक्षित था, कई
जीतने लगे।

मैंने दुश्मन से गेंद तक निकटतम दूरी के योग के साथ प्रक्षेपवक्र को ठीक करने की कोशिश की, और मुझे बहुत दिलचस्प व्यवहार मिला। मेरे रोबोट, जब वे लाभप्रद रूप से हिट नहीं कर सकते थे, अक्सर दुश्मनों को ब्लॉक करना शुरू कर देते थे, उनके प्रक्षेप पथ को तोड़ते थे और उन्हें गेंद तक चलने से रोकते थे, कभी-कभी यह बहुत ही सफलतापूर्वक और कपटी रूप से निकलता था।
अगला, मैंने कूदते समय सटीकता को ठीक किया। यदि कोई व्यक्ति मौजूदा टिक पर कूदता है, तो पहले हम दो बार 1 माइक्रोटिक करते हैं, और फिर शेष 98 माइक्रोटिक्स। मैंने भी हेयुरिस्टिक गुणांक के साथ सटीकता के नुकसान की भरपाई करने की कोशिश की है जब अधिकतम गति कुछ माइक्रोटिक्स पर पहुंच जाती है। सुधारों ने
बहुत मदद की और अधिक सटीक, पूर्व-गणना वाली हिट थीं।
इसके अलावा इस समय मैंने डिबगिंग सूचनाओं के बीच साइट पर प्रदर्शित करना शुरू कर दिया था जो कि पुनरावृत्तियों की संख्या को पूरा करने में मैं कामयाब रहा। 200 टिक्स में उनमें से 250 थे, कुल मिलाकर मेरे पास प्रति टिक प्रति मेरी रणनीति के लिए आवंटित समय के दौरान सिमुलेशन के 50,000 टिक थे।
फिर मैंने उत्परिवर्तन प्रक्षेपवक्र को चालू किया। इससे रणनीति में काफी सुधार हुआ। लगभग सभी पुनरावृत्तियों के आधे हिस्से में, यह नया प्रक्षेपवक्र नहीं था जिसका उपयोग किया गया था, लेकिन थोड़े बदले हुए मूल्यों के साथ सबसे अच्छा एक है, जिसने कहीं न कहीं, एक स्थानीय अधिकतम के लिए, कहीं भी अभिसरण करना संभव बना दिया। यह उस समय एक
मजबूत रणनीति बन गई, जिसे मैंने पहले दौर तक छोड़ने का फैसला किया था, हालांकि यह अभी भी पूरे दो सप्ताह पहले था। लेकिन कुछ दिनों के बाद वह शीर्ष पर हावी हो गई।
मैंने पूरी यादृच्छिकता से दूर होने में कुछ समय बिताया, उदाहरण के लिए, मैंने एक तिरछी खोज के साथ उस कोण को खोजने की कोशिश की, जिस पर गेंद को हिट करने के लिए रोबोट को तेज करने की आवश्यकता होती है। लेकिन यह हमेशा काम नहीं करता था, और मैंने यह पता नहीं लगाया कि इस विचार को आगे कैसे विकसित किया जाए।
मेरे रोबोटों को पता था कि केवल एक बार प्रक्षेपवक्र में कैसे कूदना है, लेकिन जब वे जमीन पर थे और कूदना चाहते थे, और फिर हवा में गेंद को मारा, तो उन्हें पता नहीं था कि जब आप गेंद को छूते हैं तो आप दूसरी बार कूद सकते हैं, जिससे गेंद को मुश्किल से मारा जा सकता है, और सिर्फ इसे धकेलना नहीं।
यह तय हो गया था, और अब सिम्युलेटर, जब उन्होंने देखा कि कोई व्यक्ति मौजूदा टिक पर गेंद को हिट कर सकता है, तो एक टिक वापस ले लिया और रोबोट को अधिकतम बल के साथ कूदने के लिए मजबूर किया। अब, जमीन पर खड़ा, रोबोट जानता था कि यह जमीन से धक्का देगा और न केवल धक्का देगा, बल्कि एक दूसरी छलांग के साथ गेंद को मारा।
मैं समझ गया कि जब नाइट्रो और एक अन्य रोबोट को जोड़ा गया था, तो पुनरावृत्तियों की कमी के कारण सब कुछ झुक जाएगा। इसके अलावा विभिन्न स्थानों पर मुझे सटीकता के साथ बड़ी समस्याएं थीं, जो मुझे नहीं पता था कि कैसे हल करना है। मैंने कोई
विश्लेषणात्मक समाधान या
प्रबंधन के किसी भी
स्मार्ट तरीके को नहीं देखा।
मुझे या तो पूरी तरह से नई रणनीति की आवश्यकता थी, या एक जादू सिम्युलेटर जो सटीकता और गति को जोड़ती है, और अंतिम चरण में मुझे इसे पार करने के लिए पर्याप्त प्रक्षेपवक्र प्रदान करेगा। मैं एक नई रणनीति (आश्चर्यजनक रूप से) के साथ नहीं आया, और एक सिम्युलेटर पर काम करना शुरू कर दिया।
"स्मार्ट सिम्युलेटर"
पहली बात मैं सटीकता से निपटना चाहता था।
मैंने एक बार में 100 मिकरोटिक का अनुकरण किया, हालांकि एक टकराव - या किसी अन्य घटना - इन एक सौ मिक्रोतिका में से एक पर हुआ। यदि आप इसे नजरअंदाज करते हैं, तो वस्तुएं वास्तविकता में (हमेशा 100 वें माइक्रोटिक्स पर) बाद में टकराती हैं, और इसलिए अलग तरह से उछलती हैं। प्रक्षेपवक्र के अंत में, यह छोटी सी गलती एक बड़ी अशुद्धि में बदल सकती है। उदाहरण के लिए, हम सोचते हैं कि गेंद दुश्मन के गोल से टकराती है, लेकिन वास्तव में यह
हमारे पोस्ट से उछल जाएगी।
यह देखना आसान है कि ऐसी स्थिति में जब सभी 100 माइक्रोटिक्स की गिनती के बजाय
i
वें माइक्रोटिक्स पर एक टक्कर होती है, यह पहली
i - 1
माइक्रोटिक्स को एक बार में गिनने के लिए पर्याप्त है (वास्तव में, भौतिकी कदम को एक निश्चित समय के लिए माना जाता है, और अब यह समय होगा।
t * (i - 1)
, जहां
t
एक मिकरोटिक के अनुरूप समय है)। अब आपको 1 माइक्रोटिक (
dt = t
) और शेष
100 - i
माइक्रोटिक्स का अनुकरण करने की आवश्यकता है। हमें सौ के बजाय सिर्फ तीन सिमुलेशन में समान परिणाम मिलता है। एकमात्र समस्या यह है कि हम यह नहीं जानते हैं कि टकराव किस सूक्ष्मदर्शी पर होगा।
सिमुलेशन के कुछ निश्चित टिक पर होने के कारण, हम एक सिमुलेशन में 1 से 100 तक किसी भी माइक्रोटिक्स की संख्या बना सकते हैं और देख सकते हैं कि कोई टक्कर है या नहीं। इस मामले में, चित्र इस तरह होगा: पहले तो कोई स्पर्श नहीं है, लेकिन एक निश्चित संख्या में माइक्रोटिक्स से शुरू होकर सौ तक एक स्पर्श है। बहुत दुर्लभ मामलों को छोड़कर, जब पहली बार में कोई संपर्क नहीं होता है, तो माइक्रोटिक्स के कुछ सेगमेंट पर एक स्पर्श होता है, और फिर फिर से कोई स्पर्श नहीं होता है।
इसलिए, मिकरोटिक को ढूंढना संभव है जिस पर सबसे खराब स्थिति में 10 सिमुलेशन के लिए एक द्विआधारी खोज का उपयोग करके टक्कर हुई। और जैसा कि पहले बताया गया है, तीन सिमुलेशन के लिए, आप सटीकता के साथ 100 माइक्रोटिक्स के माध्यम से दुनिया की स्थिति प्राप्त कर सकते हैं।
वास्तव में, टकराव के अलावा कई अन्य प्रकार के कार्यक्रम थे, और कई एक टिक में हो सकते थे, इसलिए केवल पहली घटना एक डायकोटॉमी में स्थित थी, फिर दूसरी घटना टिक डाइकोटॉमी के शेष प्रत्यय पर स्थित थी, और इसी तरह। इस प्रकार, एक टिक को सिमुलेशन के प्रति कई माइक्रोटिक्स के सेगमेंट के रूप में माना जाता था, जब तक कि सभी घटनाओं की गणना नहीं की गई थी।
इसलिए समस्याओं को सटीकता के साथ हल किया गया था। लेकिन इस तथ्य के कारण कि सिमुलेशन में 5 वस्तुएं थीं, और अंतिम नियमों के अनुसार 7 होना चाहिए था, और उनमें से सभी अक्सर दुर्घटनाग्रस्त हो गए, औसतन डायकोटोमियों को अक्सर कहा जाता था, और यह निषेधात्मक रूप से लंबा काम करता था। इसलिए, मैं सिम्युलेटर के विकास के दूसरे चरण में आगे बढ़ा - अनुकूलन।
जाहिर है, जब किसी एक रोबोट का प्रक्षेपवक्र खत्म हो जाता है, तो अन्य सभी वस्तुएं जिनमें यह रोबोट क्रैश नहीं होता है, हर बार एक ही गति करता है। यह स्पष्ट है कि एक सिम्युलेटर के साथ अपने राज्यों को पुनर्गणना - उदाहरण के लिए, अखाड़े के साथ भारी टकराव की गणना करना - आवश्यक नहीं है।
किसी विशेष रोबोट के लिए प्रक्षेपवक्र को छाँटने से पहले, यह ईमानदारी से अनुकरण करने और शेष वस्तुओं को अपने राज्यों में हर समय इंस्टेंट पर याद रखने और याद रखने के लिए पर्याप्त है, और फिर बस इन राज्यों को स्मृति से ले लें। हम ऐसी वस्तुओं को स्थिर कहते हैं, और एक रोबोट जिसके लिए प्रक्षेपवक्र को क्रमबद्ध किया जाता है, गतिशील है।
यदि किसी स्थिर एक के साथ अचानक कुछ गतिशील वस्तु प्रभावित होती है (टकराव होता है), तो हम इस स्थैतिक वस्तु को वर्तमान प्रक्षेपवक्र के अनुकरण के अंत तक गतिशील लोगों में जोड़ देते हैं। वास्तव में, स्थिर वस्तुओं के लिए भंडारण की अवस्थाओं के स्तर पर, एक दूसरे पर प्रभावों का ग्राफ बनाया जाता है, और फिर इसका उपयोग स्थैतिक वस्तुओं को गतिशील रूप से स्थानांतरित करने के लिए किया जाता है। उदाहरण के लिए, एक दुश्मन रोबोट ने गेंद को हिट किया, और हमने एक रास्ता बनाया जहां हम दुश्मन रोबोट को मारते हैं इससे पहले कि वह गेंद को हिट करे। अब गेंद आगे उड़ जाएगी, और सिमुलेशन के दौरान, जब दुश्मन रोबोट को गतिशील वस्तुओं में जोड़ा जाता है, तो यह ध्यान रखना आवश्यक है कि गेंद को गतिशील वस्तुओं में थोड़ी देर बाद जोड़ा जाना चाहिए, जिस समय हम उस पर हस्तक्षेप नहीं करेंगे, तो दुश्मन रोबोट गेंद पर टकराएगा। । सामान्य स्थिति में, यह प्रभाव ग्राफ के अनुसार पुनरावर्ती होता है।

अब सिम्युलेटर सभी वस्तुओं की गणना नहीं करता है, लेकिन केवल गतिशील वाले हैं, और यह, औसतन, सात के बजाय डेढ़ वस्तुएं हैं, और लंबी डायकोटोमियों का उपयोग अक्सर कम किया जाता है। यह बहुत जल्दी निकला, और अब अतिरिक्त रोबोट के साथ फाइनल में नहीं भुगतना पड़ा - शांत!
एक नए सिम्युलेटर के साथ 26 वें संस्करण और 200 से 100 तक कम होने वाली सिमुलेशन गहराई को पहले दौर में खेलने के लिए भेजा गया था। लेकिन इसमें कुछ कीड़े थे, और कोई स्पष्ट लाभ नहीं था।
सटीकता के साथ अंतिम समस्या बनी रही: अखाड़े के गोलाई के साथ आंदोलन। इस मामले में, पूर्ण सटीकता प्राप्त करने के लिए, ईमानदारी से 100 माइक्रोटिक्स की गणना करना आवश्यक है। समाधान आश्चर्यजनक रूप से सरल था: हमेशा फर्श को छोड़कर सभी सतहों से कूदो। कोई चक्कर नहीं - कोई समस्या नहीं।
इसके अलावा, कुछ समय के लिए मैंने अनुकूलित किया, बहस की और, चतुर रणनीतियों के साथ खेलों को देखते हुए, मैंने नए स्कोरिंग स्थिरांक लिए। यह बहुत बेहतर हो गया है, रैंकिंग में रणनीति उच्च हो गई है और 37 वें संस्करण ने फाइनल से पहले सभी बार सैंडबॉक्स में मेरी सभी रणनीतियों का सबसे अच्छा परिणाम प्राप्त किया है।
इस बिंदु से, मैंने एक क्लाउड सेवा में एक-दूसरे के खिलाफ अपनी रणनीतियों को चलाने के लिए एक 32-कोर मशीन किराए पर ली, और एक पंक्ति में सब कुछ के साथ बहुत प्रयोग करना शुरू किया। स्थिरांक बदल दिया। मैंने शत्रु के कार्यों की भविष्यवाणी करने के लिए अपनी खुद की रणनीति का उपयोग करने की कोशिश की, लेकिन इससे मेरी रणनीति के खिलाफ खेल में भी मदद नहीं मिली।
समीकरण को हल करके, उसने दुश्मन की अंतिम कार्रवाई की गणना करना सीखा और अपने आगे के व्यवहार की भविष्यवाणी करना शुरू कर दिया। नाइट्रो के लिए जोड़ा समर्थन: क्षेत्र की सतह पर एक यादृच्छिक बिंदु कार्रवाई के लिए चुना गया है। कई मामूली संपादन किए। लेकिन बहुत प्रगति नहीं हुई थी। दूसरे राउंड की शुरुआत तक 4-5 टॉप्स लगातार मुझे जीत रहे थे
फिर भी, मुझे निराशा नहीं हुई। मेरे पास दो सुधार थे जिन्हें मैंने फाइनल से पहले लागू करने की योजना बनाई थी, और मुझे उम्मीद थी कि वे रणनीति में सुधार करेंगे। मैंने तय किया कि जब तक सैंडबॉक्स अंतिम नियमों के अनुसार शुरू नहीं हो जाता, तब तक उनसे निपटना नहीं होगा और इसके बजाय डिबगिंग में समय बिताना चाहिए और अंतिम सप्ताह में पहले से ही खराब कीड़े की संभावना को कम करने के लिए पहले से ही क्या किया गया था, यह हर मिनट में गिना जाता है।
फाइनल शुरू होने से पहले अंतिम सप्ताह।
मैंने जो पहला सुधार किया, वह यही था। मैचों में, सामान्य मामले में, मेरी अधिकांश समस्याएं और कोई अन्य रणनीति तब उत्पन्न होती है जब प्रतिद्वंद्वी गेंद पर कब्जा कर लेता है। वह किसी तरह उसे मारता है, गुजरता है, सामान्य रूप से नियंत्रित करता है। गेंद के प्रक्षेपवक्र की भविष्यवाणी करना और आगे इस मामले में कुछ लाभदायक क्रियाओं की योजना बनाना असंभव है, यह तब तक "जो भी" होता है जब तक कि प्रतिद्वंद्वी गलती करता है और गेंद को मेरे रोबोट पर नियंत्रण स्थानांतरित करता है। और इसके बाद, आपको ऐसे कार्यों को नहीं करने की कोशिश करनी चाहिए जो इस तथ्य को जन्म दे सकते हैं कि गेंद फिर से दुश्मन के साथ होगी।
दूसरे शब्दों में, प्रक्षेपवक्र की योजना बनाते समय, मैं विरोधियों के संभावित पदों को ध्यान में रखना चाहता हूं और वहां गेंद को हिट न करने की कोशिश करता हूं। मैंने एक चार-आयामी संभावित क्षेत्र का उपयोग करने का निर्णय लिया (पहले तीन आयाम हैं निर्देशांक, क्यूब्स का पक्ष रोबोट के व्यास के बराबर है, और चौथा आयाम समय है), जिसे मैं भर दूंगा, यादृच्छिक दुश्मन प्रक्षेपवक्र पैदा कर रहा हूं।
बाद में, जब मैंने अपने रोबोट के लिए प्रक्षेपवक्र का मूल्यांकन किया, तो मैंने सभी क्यूब्स में योग की गणना की, जो समय के अनुरूप बिंदुओं पर गेंद को पार कर गया, और गुणांक द्वारा गुणा किया गया जो स्कोरिंग में अन्य सभी मूल्यों से अधिक है। यही है, लक्ष्य के बाद सबसे अधिक प्राथमिकता के साथ संभावित क्षेत्र को ध्यान में रखा गया था। इसने पहले 30 टिक्स के बाद सिमुलेशन से दुश्मनों को हटाने की अनुमति दी (जमीन पर रहते हुए दुश्मन इस समय के दौरान कुछ भी कर सकता था, और इस तरह के गलत पूर्वानुमान केवल हस्तक्षेप किए गए) अगर वे हवा में नहीं थे (ऐसा लग रहा था कि कोई भी अंदर नहीं होगा नाइट्रो का उपयोग करके प्रक्षेपवक्र को जटिल तरीके से बदलने के लिए हवा)।
दुश्मन के लिए यादृच्छिक प्रक्षेपवक्र उत्पन्न करके, गेंद को हिट करने के लिए न्यूनतम समय का पता लगाना संभव था। गेट के बाहर मेरे गोलकीपर के शुरुआती छलांग के साथ समस्या को हल करने के लिए यह मूल्य उपयोगी था। मेरे लिए कई गोल किए गए क्योंकि मेरा गोलकीपर जल्दी कूद गया और हवा में बेकाबू हो गया। उसके बाद, दुश्मन ने आसानी से भविष्यवाणी की कि मेरा गोलकीपर कैसे उड़ान भरेगा और यदि वह, मेरे गोलकीपर के पहुंचने से पहले गेंद के प्रक्षेपवक्र को बदल सकता है। अब मैंने गोलकीपर की छलांग रद्द कर दी, अगर दुश्मन मेरे गोलकीपर की योजना से पहले गेंद को हिट कर सकता है।

यह पता चला कि रणनीति के महत्वपूर्ण नुकसान के बिना, प्रत्येक टिक को प्रक्षेपवक्र की गणना करना संभव नहीं है, लेकिन एक के माध्यम से। रन टाइम को आधा करके, मैंने इसके पुनरावृत्तियों की औसत संख्या को दोगुना कर दिया। कुछ जादू यहां होता है। ऐसा लगता है कि यदि हम हर दूसरे टिक के प्रक्षेपवक्रों को गिनते हैं और पुनरावृत्तियों की संख्या को दोगुना करते हैं, तो पुनरावृत्तियों की औसत संख्या नहीं बदलेगी। लेकिन वास्तव में, सिम्युलेटर एक के बजाय प्रति सिमुलेशन में दो टिक (200 माइक्रोटिक्क) की गणना करेगा। और प्रक्षेपवक्र पहले से ही 50 होंगे, 100 गहरे नहीं। यही कारण है कि पुनरावृत्तियों की औसत संख्या दोगुनी हो जाएगी।
फाइनल से कुछ दिन पहले बनी। हालांकि मेरी रणनीति अच्छी गेंद पर नियंत्रण के कारण कम लक्ष्यों को स्वीकार करने लगी, लेकिन मैंने बेहतर स्कोर करना शुरू नहीं किया। इसलिए, मुझे प्रतिद्वंद्वी के लक्ष्य के लिए जल्द ही उसे एक गुणांक के साथ प्रेरित करना पड़ा। तेजी से एक गोल किया जाता है, जितना अधिक अनुपात। और यह गुणांक बाकी स्कोरिंग को पार करने के लिए बहुत अधिक बढ़ रहा है और संभावित क्षेत्र से डरो मत, जब, उदाहरण के लिए, स्कोरिंग से पहले 10 टिक को छोड़ दिया जाता है।
दुश्मन नाइट्रो भेज रहा है, जहां की एक गणना जोड़ा गया। यह एक निश्चित कदम के साथ जानवर बल का उपयोग करके किया गया था। इसके अलावा, गोलकीपर ने नाइट्रो के भंडार को फिर से भरना शुरू कर दिया, जब मेरे लक्ष्य को कुछ भी खतरा नहीं था।
दूसरा बड़ा सुधार था मिनिमैक्स का उपयोग करना। यदि स्थिर प्रक्षेपवक्र के निर्माण के दौरान दुश्मन के लिए विभिन्न प्रभाव बलों का उपयोग गेंद की उड़ान को प्रभावित करता है, तो खोज के दौरान दोनों विकल्पों पर विचार किया गया, दुश्मन के अधिकतम और न्यूनतम प्रभाव बल के साथ, और अनुमानों का न्यूनतम लिया गया।
फ़ाइनल में, जब रोबोट जमीन पर था, तब मेरे पास 7 विकल्प थे:
- एक कूद के बिना 2 कोनों;
- एक कूद के साथ 2 कोनों;
- 2 कोणों के साथ जंप और नाइट्रो कोडेक्शनल गति;
- एक छलांग और नाइट्रो के साथ 2 कोण गुरुत्वाकर्षण के लिए क्षतिपूर्ति करते हैं;
- एक छलांग के साथ 1 कोने;
- 1 कोण जंप और नाइट्रो कोडेक्शनल गति के साथ;
- एक छलांग और नाइट्रो के साथ 1 कोने गुरुत्वाकर्षण के लिए क्षतिपूर्ति करते हैं (एक बग के कारण उपयोग नहीं किया जाता है, एक लेख लिखते समय देखा गया)।
और दो विकल्प जब रोबोट हवा में है:
- क्षेत्र और यादृच्छिक प्रभाव बल की सतह पर एक यादृच्छिक बिंदु के लिए नाइट्रो;
- यादृच्छिक प्रभाव बल।
फाइनल से कुछ घंटे पहले प्रतिस्पर्धा थी, लेकिन मेरी रणनीति स्पष्ट रूप से बेहतर थी। ऐसा लग रहा था कि सब कुछ पहले ही हो चुका था, मैं एक दिन से ज्यादा नहीं सोया था, और मुझ पर कुछ भी निर्भर नहीं था। यह देखता ही रह गया। फाइनल से दो घंटे पहले, आंद्रेई ने अपने हौसले से पके हुए दाने को भेजा और सफलतापूर्वक पहला स्थान हासिल किया। उनकी भागीदारी का इतिहास यहां पाया जा सकता है:
habr.com/en/post/440398फाइनल के चरणों के बीच के अंतराल में, मैंने एक संभावित क्षेत्र को गेंद को अपने लक्ष्य से दूर धकेल दिया, चाहे वह सब कुछ हो, और यह, जैसा कि मुझे लग रहा था, ने मुझे आंद्रेई के साथ बराबरी दी। लेकिन यह पहले ही देर हो चुकी थी, क्योंकि मैंने पहले हाफ में 7 अंक गंवाए थे, और दूसरे हाफ में भी 3/3 जीत पर्याप्त नहीं थी।
RAIC एक कठिन प्रतियोगिता है और प्रतिभागियों को बहुत ही कठिन तरीके से पुरस्कार दिए जाते हैं। जब एक प्रतिभागी तालिका में सबसे ऊपर होता है, तो उसके लिए यह केवल मनोरंजन नहीं है - यह एक संघर्ष है। एक मजबूत रणनीति लिखते समय विचार करने के लिए बहुत कम चीजें हैं। किए गए प्रत्येक निर्णय महत्वपूर्ण रूप से परिणाम को प्रभावित कर सकते हैं।
रणनीति के लिए स्रोत कोड
यहां उपलब्ध होगा।