C++ में उन्नत डिज़ाइन पैटर्न: सिद्धांत से जटिल कार्यान्वयन तक
\n\nडिज़ाइन पैटर्न सॉफ्टवेयर विकास के दौरान उत्पन्न होने वाली सामान्य समस्याओं के सिद्ध समाधान हैं। यदि बुनियादी पैटर्न (Singleton, Factory, Observer) हर डेवलपर से परिचित हैं, तो उन्नत तकनीकों के लिए C++ भाषा, इसके टेम्पलेट्स, एकाधिक इनहेरिटेंस और मेटाप्रोग्रामिंग की गहरी समझ की आवश्यकता होती है। इस लेख में, हम चार शक्तिशाली पैटर्न का विश्लेषण करेंगे: Visitor, Strategy, State और CRTP — वास्तविक कोड उदाहरणों और उनके उपयोग के समय की व्याख्या के साथ।
\n\n1. Visitor पैटर्न (आगंतुक) — क्लासेस को बदले बिना कार्यक्षमता का विस्तार
\n\nVisitor पैटर्न आपको क्लासेस को स्वयं बदले बिना क्लास पदानुक्रम में नए ऑपरेशन जोड़ने की अनुमति देता है। यह विशेष रूप से तब उपयोगी होता है जब आपके पास ऑब्जेक्ट्स की एक स्थिर संरचना होती है, लेकिन उनके प्रसंस्करण के लिए एल्गोरिदम बार-बार बदलते रहते हैं।
\n\nउदाहरण: ज्यामितीय आकृतियों का प्रसंस्करण
\n\n#include <iostream>\n#include <vector>\n#include <memory>\n\n// Forward declaration\nclass Circle;\nclass Rectangle;\n\n// अमूर्त आगंतुक\nclass Visitor {\npublic:\n virtual void visit(Circle& circle) = 0;\n virtual void visit(Rectangle& rectangle) = 0;\n virtual ~Visitor() = default;\n};\n\n// अमूर्त तत्व\nclass Shape {\npublic:\n virtual void accept(Visitor& visitor) = 0;\n virtual ~Shape() = default;\n};\n\n// ठोस तत्व\nclass Circle : public Shape {\npublic:\n double radius;\n explicit Circle(double r) : radius(r) {}\n void accept(Visitor& visitor) override {\n visitor.visit(*this);\n }\n};\n\nclass Rectangle : public Shape {\npublic:\n double width, height;\n Rectangle(double w, double h) : width(w), height(h) {}\n void accept(Visitor& visitor) override {\n visitor.visit(*this);\n }\n};\n\n// ठोस आगंतुक — क्षेत्रफल की गणना\nclass AreaVisitor : public Visitor {\npublic:\n double totalArea = 0.0;\n void visit(Circle& circle) override {\n totalArea += 3.14159 * circle.radius * circle.radius;\n }\n void visit(Rectangle& rectangle) override {\n totalArea += rectangle.width * rectangle.height;\n }\n};\n\nint main() {\n std::vector<std::unique_ptr<Shape>> shapes;\n shapes.push_back(std::make_unique<Circle>(5.0));\n shapes.push_back(std::make_unique<Rectangle>(4.0, 6.0));\n\n AreaVisitor areaCalc;\n for (auto& shape : shapes) {\n shape->accept(areaCalc);\n }\n std::cout << "Total area: " << areaCalc.totalArea << std::endl;\n return 0;\n}\n\n\nकब उपयोग करें: जब आपको जटिल पदानुक्रम की वस्तुओं पर उनके कोड को बदले बिना विभिन्न ऑपरेशन करने की आवश्यकता हो। नुकसान — नए प्रकार को जोड़ने पर सभी आगंतुकों को बदलना पड़ता है।
\n\n2. Strategy पैटर्न (रणनीति) — चलते-फिरते एल्गोरिदम का लचीला परिवर्तन
\n\nStrategy परस्पर बदलने योग्य एल्गोरिदम के एक परिवार को एनकैप्सुलेट करता है और रनटाइम के दौरान उन्हें बदलने की अनुमति देता है। C++ में, इसे अक्सर std::function या वर्चुअल क्लासेस के माध्यम से कार्यान्वित किया जाता है।
उदाहरण: डेटा सॉर्टिंग सिस्टम
\n\n#include <iostream>\n#include <vector>\n#include <algorithm>\n#include <memory>\n#include <functional>\n\n// संदर्भ, जो रणनीति का उपयोग करता है\nclass Sorter {\nprivate:\n std::function<void(std::vector<int>&)> strategy_;\npublic:\n explicit Sorter(std::function<void(std::vector<int>&)> strategy)\n : strategy_(std::move(strategy)) {}\n\n void setStrategy(std::function<void(std::vector<int>&)> newStrategy) {\n strategy_ = std::move(newStrategy);\n }\n\n void sort(std::vector<int>& data) {\n if (strategy_) {\n strategy_(data);\n }\n }\n};\n\n// ठोस रणनीतियाँ\nvoid bubbleSort(std::vector<int>& da