replace macro with ProxyVector that forwards method calls to all its elements v_0
authorFrantišek Kučera <franta-hg@frantovo.cz>
Sat, 03 Jul 2021 18:56:15 +0200
branchv_0
changeset 24 114810ee2386
parent 23 8941a679299f
child 25 ba79cebde109
replace macro with ProxyVector that forwards method calls to all its elements
nbproject/configurations.xml
src/lib/ASN1ContentHandler.h
src/lib/ProxyVector.h
src/lib/XMLContentHandler.h
--- a/nbproject/configurations.xml	Fri Jul 02 00:42:01 2021 +0200
+++ b/nbproject/configurations.xml	Sat Jul 03 18:56:15 2021 +0200
@@ -50,6 +50,7 @@
           <in>BasicASN1Reader.h</in>
           <in>DOMBuildingXMLContentHandler.h</in>
           <in>GenericASN1ContentHandler.h</in>
+          <in>ProxyVector.h</in>
           <in>TransactionalBuffer.h</in>
           <in>XMLContentHandler.h</in>
         </df>
@@ -133,6 +134,8 @@
             tool="3"
             flavor2="0">
       </item>
+      <item path="src/lib/ProxyVector.h" ex="false" tool="3" flavor2="0">
+      </item>
       <item path="src/lib/TransactionalBuffer.h" ex="false" tool="3" flavor2="0">
       </item>
       <item path="src/lib/XMLContentHandler.h" ex="false" tool="3" flavor2="0">
@@ -198,6 +201,8 @@
             tool="3"
             flavor2="0">
       </item>
+      <item path="src/lib/ProxyVector.h" ex="false" tool="3" flavor2="0">
+      </item>
       <item path="src/lib/TransactionalBuffer.h" ex="false" tool="3" flavor2="0">
       </item>
       <item path="src/lib/XMLContentHandler.h" ex="false" tool="3" flavor2="0">
--- a/src/lib/ASN1ContentHandler.h	Fri Jul 02 00:42:01 2021 +0200
+++ b/src/lib/ASN1ContentHandler.h	Sat Jul 03 18:56:15 2021 +0200
@@ -22,6 +22,8 @@
 #include <iomanip>
 #include <cmath>
 
+#include "ProxyVector.h"
+
 namespace relpipe {
 namespace in {
 namespace asn1 {
@@ -264,65 +266,61 @@
 
 class ASN1ContentHandlerProxy : public ASN1ContentHandler {
 private:
-	std::vector<std::shared_ptr<ASN1ContentHandler>> handlers;
+	ProxyVector<ASN1ContentHandler> handlers;
 public:
 
 	void addHandler(std::shared_ptr<ASN1ContentHandler> handler) {
 		handlers.push_back(handler);
 	}
 
-#define handler for (auto ___h : handlers) ___h
-
 	void writeStreamStart() override {
-		handler->writeStreamStart();
+		handlers.forward(&ASN1ContentHandler::writeStreamStart);
 	}
 
 	void writeStreamEnd() override {
-		handler->writeStreamEnd();
+		handlers.forward(&ASN1ContentHandler::writeStreamEnd);
 	}
 
 	void writeCollectionStart(CollectionType type) override {
-		handler->writeCollectionStart(type);
+		handlers.forward(&ASN1ContentHandler::writeCollectionStart, type);
 	}
 
 	void writeCollectionEnd() override {
-		handler->writeCollectionEnd();
+		handlers.forward(&ASN1ContentHandler::writeCollectionEnd);
 	}
 
 	void writeBoolean(bool value) override {
-		handler->writeBoolean(value);
+		handlers.forward(&ASN1ContentHandler::writeBoolean, value);
 	}
 
 	void writeNull() override {
-		handler->writeNull();
+		handlers.forward(&ASN1ContentHandler::writeNull);
 	}
 
 	void writeInteger(Integer value) override {
-		handler->writeInteger(value);
+		handlers.forward(&ASN1ContentHandler::writeInteger, value);
 	}
 
 	void writeTextString(StringType type, std::string value) override {
-		handler->writeTextString(type, value);
+		handlers.forward(&ASN1ContentHandler::writeTextString, type, value);
 	}
 
 	void writeOctetString(std::string value) override {
-		handler->writeOctetString(value);
+		handlers.forward(&ASN1ContentHandler::writeOctetString, value);
 	}
 
 	void writeBitString(std::vector<bool> value) override {
-		handler->writeBitString(value);
+		handlers.forward(&ASN1ContentHandler::writeBitString, value);
 	}
 
 	void writeOID(ObjectIdentifier value) override {
-		handler->writeOID(value);
+		handlers.forward(&ASN1ContentHandler::writeOID, value);
 	}
 
 	void writeDateTime(DateTimeType type, DateTime value) override {
-		handler->writeDateTime(type, value);
+		handlers.forward(&ASN1ContentHandler::writeDateTime, type, value);
 	}
 
-#undef handler
-
 };
 
 
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/src/lib/ProxyVector.h	Sat Jul 03 18:56:15 2021 +0200
@@ -0,0 +1,47 @@
+/**
+ * Relational pipes
+ * Copyright © 2021 František Kučera (Frantovo.cz, GlobalCode.info)
+ *
+ * This program is free software: you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License as published by
+ * the Free Software Foundation, version 3 of the License.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
+ * GNU General Public License for more details.
+ *
+ * You should have received a copy of the GNU General Public License
+ * along with this program. If not, see <http://www.gnu.org/licenses/>.
+ */
+#pragma once
+
+#include <memory>
+
+namespace relpipe {
+namespace in {
+namespace asn1 {
+namespace lib {
+
+template <typename Class>
+class ProxyVector : public std::vector<std::shared_ptr<Class>> {
+public:
+
+	/**
+	 * Call given method on all instances.
+	 *
+	 * @param method a method of Class
+	 * @param arguments arguments of the method
+	 */
+	template<typename Method, typename... Arguments> void forward(Method method, Arguments&&... arguments) {
+		for (auto& h : * this) {
+			// TODO: optionally handle/collect exceptions
+			(h.get()->*method)(arguments...);
+		}
+	}
+};
+
+}
+}
+}
+}
--- a/src/lib/XMLContentHandler.h	Fri Jul 02 00:42:01 2021 +0200
+++ b/src/lib/XMLContentHandler.h	Sat Jul 03 18:56:15 2021 +0200
@@ -16,7 +16,7 @@
  */
 #pragma once
 
-#include <vector>
+#include "ProxyVector.h"
 
 namespace relpipe {
 namespace in {
@@ -39,33 +39,29 @@
 
 class XMLContentHandlerProxy : XMLContentHandler {
 private:
-	std::vector<std::shared_ptr<XMLContentHandler>> handlers;
+	ProxyVector<XMLContentHandler> handlers;
 public:
 
 	void addHandler(std::shared_ptr<XMLContentHandler> handler) {
 		handlers.push_back(handler);
 	}
 
-#define handler for (auto ___h : handlers) ___h
-
 	void writeStartElement(const std::string& name, const std::vector<std::string>& attributes = {}) override {
-		handler->writeStartElement(name, attributes);
+		handlers.forward(&XMLContentHandler::writeStartElement, name, attributes);
 	}
 
 	void writeEndElement() override {
-		handler->writeEndElement();
+		handlers.forward(&XMLContentHandler::writeEndElement);
 	}
 
 	void writeCharacters(const std::string& value) override {
-		handler->writeCharacters(value);
+		handlers.forward(&XMLContentHandler::writeCharacters, value);
 	}
 
 	void writeComment(const std::string& value, bool addSpaces = true) override {
-		handler->writeComment(value, addSpaces);
+		handlers.forward(&XMLContentHandler::writeComment, value, addSpaces);
 	}
 
-#undef handler
-
 };
 
 }