Skip to content
Snippets Groups Projects
Commit 09d03e97 authored by berleon's avatar berleon
Browse files

Add evaluation & small fixes for transaction logs

parent 943ed45a
No related branches found
No related tags found
No related merge requests found
%% Cell type:code id: tags:
``` python
%matplotlib inline
import numpy as np
import matplotlib.pyplot as plt
import json
import os
from pylab import rcParams
rcParams['figure.figsize'] = 10, 6
```
%% Cell type:code id: tags:
``` python
log_dir = 'log'
```
%% Cell type:code id: tags:
``` python
snapshots = {}
for filename in os.listdir(log_dir):
with open(os.path.join(log_dir, filename), 'r') as f:
snapshots[filename] = json.load(f)
```
%% Cell type:code id: tags:
``` python
for filename, snap in snapshots.items():
if len(snap) != 9:
os.remove(os.path.join(log_dir, filename))
```
%% Cell type:code id: tags:
``` python
snapshots = {fname: snap for fname, snap in snapshots.items() if len(snap) == 9}
print("got {} snapshots".format(len(snapshots)))
```
%% Cell type:code id: tags:
``` python
next(iter(snapshots.values()))
```
%% Cell type:code id: tags:
``` python
def get_all_values(prefix):
all_values = []
for snap in snapshots.values():
snap_values = []
for node, value in snap.items():
if node.startswith(prefix):
snap_values.append(value[0])
all_values.append(snap_values)
return np.array(all_values)
get_all_values('balanced')
```
%% Cell type:code id: tags:
``` python
labels = ['generous', 'balanced', 'greedy']
gbg = np.stack([get_all_values(prefix).flatten() for prefix in labels]).T
```
%% Cell type:code id: tags:
``` python
gbg.shape
```
%% Cell type:code id: tags:
``` python
plt.boxplot(gbg)
plt.xticks(np.arange(1, len(labels)+1), labels)
plt.show()
```
%% Cell type:code id: tags:
``` python
```
{"greedy_2":[84],"balanced_1":[233],"greedy_1":[144],"balanced_2":[113],"greedy_0":[61],"balanced_0":[235],"generous_1":[5],"generous_2":[6],"generous_0":[19]}
{"balanced_1":[108],"greedy_2":[123],"greedy_1":[112],"balanced_2":[40],"greedy_0":[40],"balanced_0":[387],"generous_1":[38],"generous_2":[21],"generous_0":[31]}
{"greedy_2":[248],"balanced_1":[110],"greedy_1":[134],"balanced_2":[143],"greedy_0":[56],"balanced_0":[206],"generous_1":[0],"generous_2":[1],"generous_0":[2]}
{"greedy_2":[77],"balanced_1":[147],"greedy_1":[236],"balanced_2":[106],"greedy_0":[141],"balanced_0":[172],"generous_1":[0],"generous_2":[20],"generous_0":[1]}
{"greedy_2":[31],"balanced_1":[78],"greedy_1":[147],"balanced_2":[272],"greedy_0":[58],"balanced_0":[147],"generous_1":[119],"generous_2":[16],"generous_0":[32]}
{"greedy_2":[91],"balanced_1":[122],"greedy_1":[174],"balanced_2":[171],"greedy_0":[64],"balanced_0":[151],"generous_1":[100],"generous_2":[1],"generous_0":[26]}
{"greedy_2":[39],"balanced_1":[21],"greedy_1":[407],"balanced_2":[132],"greedy_0":[120],"balanced_0":[92],"generous_1":[23],"generous_2":[65],"generous_0":[1]}
......@@ -92,6 +92,10 @@ public abstract class AbstractNode extends UntypedActor implements Serializable
public Promise<Snapshot> makeSnapshot() throws InterruptedException {
return makeSnapshot(true);
}
public Promise<Snapshot> makeSnapshot(boolean useDelay) throws InterruptedException{
String prefix = "";
if (this instanceof SuperVisorImpl) {
prefix = "supervisor";
......@@ -110,13 +114,15 @@ public abstract class AbstractNode extends UntypedActor implements Serializable
int i = 0;
for (ActorRef act : getKnownNeighbors().values()) {
if(i % 3 == 0){
if (useDelay) {
try {
//Add a little delay now and then
//Add a little useDelay now and then
Thread.sleep(500);
} catch (InterruptedException ex) {
Exceptions.printStackTrace(ex);
}
}
}
act.tell(new SnapShotBegin(this.currentSnapshotToken), self());
}
return this.snapshot.promise();
......
......@@ -5,25 +5,41 @@ import fucoin.actions.snap.SnapShotSaveState;
import org.json.JSONObject;
import scala.concurrent.Promise;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.*;
import java.util.concurrent.ConcurrentHashMap;
public class Snapshot {
public HashMap<String, Integer> states = new HashMap<>();
public List<SnapshotTransaction> transactions = new ArrayList<>();
public Map<String, Integer> states = new ConcurrentHashMap<String, Integer>();
public List<SnapshotTransaction> transactions = Collections.synchronizedList(new ArrayList<>());
private Promise<Snapshot> complete = Futures.promise();
@Override
public String toString() {
return "Snapshot{" +
"states=" + states +
", transactions=" + transactions +
'}';
StringBuilder sb = new StringBuilder();
sb.append("Snapshot {\n");
sb.append(" States {\n");
for (String name : states.keySet()) {
sb.append(" " + name + ": " + states.get(name) + "\n");
}
sb.append(" }\n");
sb.append(" Transactions {\n");
for (int i = 0; i < transactions.size(); i++) {
SnapshotTransaction ts = transactions.get(i);
sb.append(" " + ts.amount + " FU's from " + ts.sender + " to " + ts.receiver + "\n");
}
sb.append(" }\n");
sb.append("}\n");
return sb.toString();
}
public JSONObject toJson() {
return null;
JSONObject obj = new JSONObject();
for (String key : states.keySet()) {
obj.append(key, states.get(key));
}
return obj;
}
public void addState(String name, int amount) {
......
......@@ -26,7 +26,13 @@ public class SnapShotSaveState extends SnapAction {
for (ActorRef node : abstractNode.getKnownNeighbors().values()) {
node.tell(new SnapShotEnd(), self);
}
try {
if (! snap.promise().isCompleted()) {
snap.completed();
}
} catch (IllegalStateException e) {
throw e;
}
}
}
}
......@@ -4,7 +4,6 @@ import akka.actor.ActorRef;
import akka.actor.UntypedActorContext;
import fucoin.AbstractNode;
import fucoin.SnapshotTransaction;
import fucoin.actions.Action;
public class SnapShotSaveTransaction extends SnapAction {
public SnapshotTransaction transaction;
......
......@@ -2,6 +2,7 @@ package fucoin.configurations;
import akka.actor.ActorRef;
import akka.dispatch.Futures;
import akka.dispatch.OnComplete;
import akka.dispatch.OnSuccess;
import akka.pattern.Patterns;
import fucoin.Snapshot;
......@@ -11,19 +12,24 @@ import fucoin.actions.transaction.ActionGetAmount;
import fucoin.actions.transaction.ActionGetAmountAnswer;
import fucoin.actions.transaction.ActionNotifyObserver;
import fucoin.configurations.internal.ConfigurationName;
import fucoin.supervisor.SuperVisorLogImpl;
import org.apache.commons.math3.distribution.EnumeratedDistribution;
import org.apache.commons.math3.util.Pair;
import org.json.JSONObject;
import scala.Function1;
import scala.PartialFunction;
import scala.concurrent.Await;
import scala.concurrent.Future;
import scala.concurrent.Promise;
import scala.runtime.BoxedUnit;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
import scala.util.Try;
import java.io.File;
import java.io.PrintWriter;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.text.DateFormat;
import java.text.SimpleDateFormat;
import java.util.*;
import java.util.stream.Collectors;
import java.util.stream.Stream;
import org.openide.util.Exceptions;
......@@ -101,11 +107,12 @@ class WalletSimulation {
@ConfigurationName("GGBWallet")
public class GGBWalletConfiguration extends AbstractConfiguration {
private static int n_generous = 1;
private static int n_greedy = 1;
private static int n_balanced = 1;
private static double n_steps = 40000;
private static String log_filename = "log.json";
private static int n_generous = 3;
private static int n_greedy = 3;
private static int n_balanced = 3;
private static int n_steps = 500;
private static String logDirectory = "log";
private Map<String, WalletSimulation> simulations;
private HashMap<String,ActorRef> walletMap;
......@@ -127,9 +134,13 @@ public class GGBWalletConfiguration extends AbstractConfiguration {
private int currentStep = 0;
private Promise<Void> simulationFinished = Futures.promise();
private double start;
static {
File logDir = new File(logDirectory);
if (!logDir.exists()) {
logDir.mkdir();
}
}
@Override
public void run() {
simulations = new HashMap<>();
......@@ -185,23 +196,40 @@ public class GGBWalletConfiguration extends AbstractConfiguration {
simulations.put(name, new WalletSimulation(name, allWalletNames, BALANCED_PROBABILITY,
BALANCED_MIN, BALANCED_MAX, BALANCED_ADAPTION));
}
start = System.currentTimeMillis() / 1000.;
try {
this.nextTransaction();
} catch (InterruptedException ex) {
Exceptions.printStackTrace(ex);
}
simulationFinished.future().onSuccess(new OnSuccess<Void>() {
simulationFinished.future().andThen(new OnComplete<Void>() {
@Override
public void onComplete(Throwable failure, Void success) throws Throwable {
final boolean noDelay = false;
GGBWalletConfiguration.this.makeSnapshot(noDelay).future().onSuccess(
new OnSuccess<Snapshot>() {
@Override
public void onSuccess(Void result) {
// You can start your algorithm here if you want to.
// Alternatively, you can also notify the user that all transactions are finished
System.out.println("All random transactions finished!");
public void onSuccess(Snapshot snap) throws Throwable {
JSONObject json = snap.toJson();
TimeZone tz = TimeZone.getTimeZone("UTC");
DateFormat df = new SimpleDateFormat("yyyy-MM-dd'T'HH:mm'Z'");
df.setTimeZone(tz);
String nowAsISO = df.format(new Date());
Path logFilename = Paths.get(GGBWalletConfiguration.logDirectory, nowAsISO + ".json");
try(PrintWriter f = new PrintWriter(logFilename.toString())) {
f.println(json.toString());
}
System.out.println("SNAPSHOT saved under: " + logFilename.toString());
}
}
, context().dispatcher());
}
}, context().dispatcher());
}
private void nextTransaction() throws InterruptedException {
for(;currentStep < n_steps; currentStep++) {
for (WalletSimulation currentWallet : simulations.values()) {
if(currentWallet.willSend()){
String receiverName = currentWallet.sampleReceiver();
......@@ -229,6 +257,10 @@ public class GGBWalletConfiguration extends AbstractConfiguration {
}
}
}
if (simulationFinished != null) {
simulationFinished.success(null);
simulationFinished = null;
}
}
......@@ -246,19 +278,6 @@ public class GGBWalletConfiguration extends AbstractConfiguration {
}
return 0;
}
@Override
ActorRef initSupervisor() {
superVisor = context().actorOf(
SuperVisorLogImpl.props(log_filename), "SuperVisorImpl");
// Don't ask.
try {
Thread.sleep(200);
} catch (InterruptedException e) {
e.printStackTrace();
}
return superVisor;
}
@Override
public void onReceive(Object message) {
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Please register or to comment