[Rsiena-commits] r237 - in pkg/RSienaTest/src/network: . layers

noreply at r-forge.r-project.org noreply at r-forge.r-project.org
Mon Aug 5 08:26:08 CEST 2013


Author: ortmann
Date: 2013-08-05 08:26:08 +0200 (Mon, 05 Aug 2013)
New Revision: 237

Added:
   pkg/RSienaTest/src/network/layers/
   pkg/RSienaTest/src/network/layers/DistanceTwoLayer.cpp
   pkg/RSienaTest/src/network/layers/DistanceTwoLayer.h
   pkg/RSienaTest/src/network/layers/NetworkLayer.h
Modified:
   pkg/RSienaTest/src/network/IncidentTieIterator.h
Log:
add:
	Abstract class NetworkLayer implementing INetworkChangeListener
	DistanceTwoLayer maintaining all neighbors at distance two for a given actor
changes:
	added DistanceTwoLayer to IncidentTieIterator friends list

Modified: pkg/RSienaTest/src/network/IncidentTieIterator.h
===================================================================
--- pkg/RSienaTest/src/network/IncidentTieIterator.h	2013-08-05 06:24:20 UTC (rev 236)
+++ pkg/RSienaTest/src/network/IncidentTieIterator.h	2013-08-05 06:26:08 UTC (rev 237)
@@ -26,7 +26,7 @@
 class IncidentTieIterator: public ITieIterator {
 	// The class Network needs access to the private constructor.
 	friend class Network;
-	friend class DistanceTwoView;
+	friend class DistanceTwoLayer;
 
 public:
 	IncidentTieIterator();

Added: pkg/RSienaTest/src/network/layers/DistanceTwoLayer.cpp
===================================================================
--- pkg/RSienaTest/src/network/layers/DistanceTwoLayer.cpp	                        (rev 0)
+++ pkg/RSienaTest/src/network/layers/DistanceTwoLayer.cpp	2013-08-05 06:26:08 UTC (rev 237)
@@ -0,0 +1,163 @@
+/*
+ * DistanceTwoLayer.cpp
+ *
+ *  Created on: 05.08.2013
+ *      Author: ortmann
+ */
+
+#include "DistanceTwoLayer.h"
+
+#include <vector>
+#include <math.h>
+
+#include "../IncidentTieIterator.h"
+#include "../iterators/UnionTieIterator.h"
+
+namespace siena {
+
+using namespace std;
+
+typedef map<int, int> TieMap;
+
+DistanceTwoLayer::DistanceTwoLayer(const Network& rNetwork) :
+		NetworkLayer(), //
+		lpAdjacencies(new map<int, int> [rNetwork.n()]) {
+	if (rNetwork.isOneMode()) {
+		initializeOneMode(rNetwork);
+	} else {
+		initializeTwoMode(rNetwork);
+	}
+}
+
+DistanceTwoLayer::~DistanceTwoLayer() {
+	delete[] lpAdjacencies;
+}
+
+void DistanceTwoLayer::initializeOneMode(const Network& rNetwork) {
+	for (int i = 0; i < rNetwork.n(); ++i) {
+		std::vector<int> neighAtDistOne;
+		// avoid the time to copy
+		neighAtDistOne.reserve(rNetwork.outDegree(i) + rNetwork.inDegree(i));
+		// we could do this all with UnionIterators but it is much slower
+		for (UnionTieIterator iter(rNetwork.inTies(i), rNetwork.outTies(i));
+				iter.valid(); iter.next()) {
+			// take care of loops
+			if (iter.actor() != i) {
+				neighAtDistOne.push_back(iter.actor());
+			}
+		}
+		vector<int>::const_iterator iterEnd = neighAtDistOne.end();
+		for (vector<int>::const_iterator outerIter = neighAtDistOne.begin();
+				outerIter != iterEnd; ++outerIter) {
+			int ego = *outerIter;
+			for (vector<int>::const_iterator innerIter = outerIter + 1;
+					innerIter != iterEnd; ++innerIter) {
+				modifyTieValue(ego, *innerIter, 1);
+			}
+		}
+	}
+}
+
+void DistanceTwoLayer::initializeTwoMode(const Network& rNetwork) {
+	// this is a two mode network so we do not need to check for loops
+	for (int i = 0; i < rNetwork.m(); ++i) {
+		for (IncidentTieIterator outerIter = rNetwork.inTies(i);
+				outerIter.valid(); outerIter.next()) {
+			int outerActor = outerIter.actor();
+			// copy the iterator
+			IncidentTieIterator innerIter(outerIter);
+			// move to the next position
+			innerIter.next();
+			for (; innerIter.valid(); innerIter.next()) {
+				modifyTieValue(outerActor, innerIter.actor(), 1);
+			}
+		}
+	}
+}
+
+void DistanceTwoLayer::modifyTieValue(int ego, int alter, int val) {
+	updateSingleTieValue(ego, alter, val);
+	updateSingleTieValue(alter, ego, val);
+}
+
+void DistanceTwoLayer::modify2PathCountOneMode(const Network& rNetwork, int ego,
+		int alter, int val) {
+	// if it is a loop or the edge (alter,ego) exists we have nothing to do
+	if (ego == alter || rNetwork.hasEdge(alter, ego)) {
+		return;
+	}
+	for (UnionTieIterator iter(
+			UnionTieIterator(rNetwork.outTies(ego), rNetwork.inTies(ego)),
+			UnionTieIterator(rNetwork.outTies(alter), rNetwork.inTies(alter)),
+			ego, alter); iter.valid(); iter.next()) {
+		int curNeighbor = iter.actor();
+		// check whether the current neighbor is ego or alter itself
+		if (curNeighbor != ego && curNeighbor != alter) {
+			// if it is a common neighbor it creates a new 2-path with both
+			if (iter.isCommonNeighbor()) {
+				modifyTieValue(curNeighbor, ego, val);
+				modifyTieValue(curNeighbor, alter, val);
+			} else {
+				// get the inactive iter id (ego or alter)
+				int inactiveIterID = iter.getInactiveIterID();
+				modifyTieValue(curNeighbor, inactiveIterID, val);
+			}
+		}
+	}
+}
+
+void DistanceTwoLayer::modify2PathCountTwoMode(const Network& rNetwork, int ego,
+		int alter, int val) {
+	for (IncidentTieIterator iter = rNetwork.inTies(alter); iter.valid();
+			iter.next()) {
+		if (iter.actor() != ego) {
+			modifyTieValue(ego, iter.actor(), val);
+		}
+	}
+}
+
+void DistanceTwoLayer::onTieIntroductionEvent(const Network& rNetwork,
+		const int ego, const int alter) {
+	if (rNetwork.isOneMode()) {
+		modify2PathCountOneMode(rNetwork, ego, alter, 1);
+	} else {
+		modify2PathCountTwoMode(rNetwork, ego, alter, -1);
+	}
+}
+
+void DistanceTwoLayer::onTieWithdrawalEvent(const Network& rNetwork,
+		const int ego, const int alter) {
+	if (rNetwork.isOneMode()) {
+		modify2PathCountOneMode(rNetwork, ego, alter, -1);
+	} else {
+		modify2PathCountTwoMode(rNetwork, ego, alter, -1);
+	}
+}
+
+void DistanceTwoLayer::onNetworkClearEvent(const Network& rNetwork) {
+	for (int i = 0; i < rNetwork.n(); ++i) {
+		lpAdjacencies[i].clear();
+	}
+}
+
+IncidentTieIterator DistanceTwoLayer::getDistanceTwoNeighbors(int ego) const {
+	return IncidentTieIterator(lpAdjacencies[ego]);
+}
+
+void DistanceTwoLayer::updateSingleTieValue(int ego, int alter, int val) {
+	TieMap& egoMap = lpAdjacencies[ego];
+	TieMap::iterator iter = egoMap.lower_bound(alter);
+	// we found the element
+	if (iter != egoMap.end() && !egoMap.key_comp()(alter, iter->first)) {
+		int newVal = iter->second + val;
+		if (newVal) {
+			iter->second = newVal;
+		} else {
+			egoMap.erase(iter);
+		}
+	} else {
+		egoMap.insert(iter, TieMap::value_type(alter, val));
+	}
+}
+
+} /* namespace siena */

Added: pkg/RSienaTest/src/network/layers/DistanceTwoLayer.h
===================================================================
--- pkg/RSienaTest/src/network/layers/DistanceTwoLayer.h	                        (rev 0)
+++ pkg/RSienaTest/src/network/layers/DistanceTwoLayer.h	2013-08-05 06:26:08 UTC (rev 237)
@@ -0,0 +1,50 @@
+/*
+ * DistanceTwoLayer.h
+ *
+ *  Created on: 05.08.2013
+ *      Author: ortmann
+ */
+
+#ifndef DISTANCETWOLAYER_H_
+#define DISTANCETWOLAYER_H_
+
+#include <map>
+
+#include "NetworkLayer.h"
+#include "../Network.h"
+
+namespace siena {
+
+class DistanceTwoLayer: public NetworkLayer {
+public:
+	DistanceTwoLayer(const Network& rNetwork);
+	virtual ~DistanceTwoLayer();
+
+	void initializeOneMode(const Network& rNetwork);
+
+	void initializeTwoMode(const Network& rNetwork);
+
+	void onTieIntroductionEvent(const Network& rNetwork, const int ego,
+			const int alter);
+	void onTieWithdrawalEvent(const Network& rNetwork, const int ego,
+			const int alter);
+
+	void onNetworkClearEvent(const Network& rNetwork);
+
+	IncidentTieIterator getDistanceTwoNeighbors(int ego) const;
+private:
+	void updateSingleTieValue(int ego, int alter, int val);
+
+	void modifyTieValue(int ego, int alter, int val);
+
+	void modify2PathCountOneMode(const Network& rNetwork, int ego, int alter,
+			int val);
+
+	void modify2PathCountTwoMode(const Network& rNetwork, int ego, int alter,
+			int val);
+
+	std::map<int, int>* lpAdjacencies;
+};
+
+} /* namespace siena */
+#endif /* DISTANCETWOLAYER_H_ */

Added: pkg/RSienaTest/src/network/layers/NetworkLayer.h
===================================================================
--- pkg/RSienaTest/src/network/layers/NetworkLayer.h	                        (rev 0)
+++ pkg/RSienaTest/src/network/layers/NetworkLayer.h	2013-08-05 06:26:08 UTC (rev 237)
@@ -0,0 +1,31 @@
+/*
+ * NetworkLayer.h
+ *
+ *  Created on: 05.08.2013
+ *      Author: ortmann
+ */
+
+#ifndef NETWORKLAYER_H_
+#define NETWORKLAYER_H_
+
+#include "../INetworkChangeListener.h"
+
+namespace siena {
+class NetworkLayer: public INetworkChangeListener {
+public:
+	virtual ~NetworkLayer() {
+	}
+protected:
+	virtual void initializeOneMode(const Network& rNetwork) = 0;
+	NetworkLayer() :
+			INetworkChangeListener() {
+	}
+private:
+	// disable copy constructor and copy assignment
+	NetworkLayer& operator=(const NetworkLayer& rhs);
+	NetworkLayer(const NetworkLayer& rhs);
+};
+
+} /* namespace siena */
+
+#endif /* NETWORKLAYER_H_ */



More information about the Rsiena-commits mailing list