In [13]:
# Import necessary tools
import pandas as pd
import matplotlib.pyplot as plt
import scipy  as sp
import os

In [14]:
# Set environment variables for bash
WD = os.getcwd()

SRC_DIR = WD + "/.."
BUILD_DIR = WD + "/../../build"
GRAPH_DIR=BUILD_DIR + "/statistics/graphs" # Where we will place the graph plots
RES_IN=BUILD_DIR + "/experiment/res.csv"

%env SRC_DIR=$SRC_DIR
%env BUILD_DIR=$BUILD_DIR
%env GRAPH_DIR=$GRAPH_DIR
%env CSV_DIR=$CSV_DIR
%env RES_IN=$RES_IN


env: SRC_DIR=/home/anthonyd973/Git/swarmlist-list-based/src/statistics/..
env: BUILD_DIR=/home/anthonyd973/Git/swarmlist-list-based/src/statistics/../../build
env: GRAPH_DIR=/home/anthonyd973/Git/swarmlist-list-based/src/statistics/../../build/statistics/graphs
env: CSV_DIR=$CSV_DIR
env: RES_IN=/home/anthonyd973/Git/swarmlist-list-based/src/statistics/../../build/experiment/res.csv

Data fetching

  • Extract bzipped result. One may put their own results under <git's root>/build/experiment instead, in which case the extracting will be ignored.

In [15]:
%%bash

if [ ! -e "$BUILD_DIR/experiment" ]
then

    ARCHIVE="$SRC_DIR/statistics/results.tbz"
    
    mkdir -p "$BUILD_DIR"
    mkdir -p "$GRAPH_DIR"
    tar -xjf "$ARCHIVE" -C "$BUILD_DIR"
fi

Data analyzing

  • Setup variables

In [16]:
INDEX_NAMES = ["Protocol", "Topology", "Packet drop rate", "Num. robots"]
COLUMN_NAMES=["Consensus time", "Num. tx entries", "Num. rx entries", "Mean tx bandwidth", "Mean rx bandwidth"]
PROTOCOLS=["consensus"] # Our experiments only used the 'consensus' protocol, i.e.,
                        # placing all the robots and waiting for consensus to be reached.
TOPOLOGIES=["line", "cluster", "scalefree"]
DROP_RATES=[0, 0.25, 0.5, 0.75]
  • Crunch data

In [17]:
# Gets results' data and renames the axes
def readResults(filename):
    df = pd.read_csv(filename, index_col=[0,1,2,3])
    df.index.names = INDEX_NAMES
    df.columns = COLUMN_NAMES
    return df

In [18]:
# Gives statistical data for each {protocol, topology, drop rate, num robots}
# configuration about the specified column.
def crunchColumnByConfig(df, columnName):
    # Get column's data
    ret = df.xs(columnName, axis=1)
    # Then group experiments by configuration
    ret = ret.groupby(level=[0,1,2,3])
    # Then do some pandas magic stuff
    ret = ret.apply(pd.Series.reset_index, drop=True).unstack().transpose().describe().transpose()
    return ret

In [19]:
data = readResults(RES_IN)
consensusData = crunchColumnByConfig(data, "Consensus time")
consensusData


Out[19]:
count mean std min 25% 50% 75% max
Protocol Topology Packet drop rate Num. robots
consensus cluster 0.00 10 30.0 3.833333 0.592093 3.0 3.25 4.0 4.00 5.0
50 30.0 13.966667 1.902509 11.0 13.00 13.0 15.00 18.0
100 29.0 27.896552 2.743106 24.0 26.00 27.0 29.00 35.0
300 28.0 89.071429 9.827884 66.0 84.00 90.0 96.00 112.0
500 30.0 154.433333 20.538749 108.0 149.25 156.0 162.50 194.0
800 29.0 255.586207 23.404086 229.0 241.00 248.0 254.00 323.0
1000 28.0 322.821429 35.004818 247.0 301.75 315.0 331.25 392.0
2000 28.0 757.571429 117.443896 605.0 621.75 779.0 810.50 1003.0
3000 27.0 1147.481481 152.180654 911.0 989.50 1200.0 1209.00 1458.0
5000 27.0 2136.000000 387.767178 1516.0 1998.00 2013.0 2483.50 2996.0
0.25 10 30.0 4.800000 0.714384 4.0 4.00 5.0 5.00 6.0
50 30.0 18.366667 3.468910 15.0 16.00 17.5 19.00 28.0
100 29.0 35.206897 4.329131 28.0 32.00 35.0 37.00 47.0
300 28.0 128.035714 17.019558 99.0 114.25 130.0 137.50 166.0
500 30.0 241.700000 48.982861 183.0 209.25 227.0 258.75 384.0
700 29.0 354.724138 80.703999 251.0 299.00 336.0 381.00 664.0
1000 28.0 498.678571 83.209710 332.0 445.75 481.0 545.75 720.0
2000 28.0 1148.464286 310.777577 878.0 956.00 1048.0 1250.75 2364.0
0.50 10 30.0 6.366667 1.711691 4.0 5.00 6.0 7.00 11.0
50 30.0 27.900000 6.910013 18.0 23.25 27.0 31.00 47.0
100 29.0 57.758621 10.002340 44.0 50.00 57.0 62.00 83.0
300 28.0 207.642857 34.314681 161.0 187.50 195.5 222.50 296.0
500 30.0 425.133333 60.598585 317.0 382.50 420.5 473.25 550.0
700 29.0 684.172414 212.233037 520.0 572.00 609.0 695.00 1293.0
1000 28.0 1035.035714 252.728735 773.0 874.50 979.0 1109.75 2042.0
1500 29.0 1770.655172 369.602516 1260.0 1485.00 1739.0 1927.00 2944.0
0.75 10 30.0 11.100000 5.040183 6.0 7.25 10.0 12.75 26.0
50 30.0 59.433333 22.171251 34.0 44.00 53.0 64.00 122.0
100 29.0 141.758621 37.304400 94.0 109.00 132.0 167.00 221.0
200 28.0 299.500000 81.755960 222.0 243.75 272.5 307.75 555.0
... ... ... ... ... ... ... ... ... ... ...
scalefree 0.00 1000 28.0 463.678571 84.707800 307.0 410.00 469.5 499.75 749.0
2000 30.0 1047.666667 208.059728 790.0 919.75 994.5 1183.75 1497.0
3000 30.0 1747.300000 388.802330 1199.0 1496.75 1755.5 2064.00 2658.0
5000 29.0 3371.517241 632.640364 2493.0 2990.00 3472.0 3492.00 4775.0
0.25 10 30.0 8.300000 1.534657 6.0 7.00 8.0 10.00 11.0
50 30.0 44.900000 7.906130 28.0 40.00 44.5 51.75 61.0
100 30.0 90.233333 19.302820 56.0 78.75 87.0 102.50 133.0
300 28.0 274.071429 66.465769 178.0 224.50 268.0 309.75 449.0
500 30.0 424.200000 89.123471 284.0 364.00 426.5 478.00 640.0
700 28.0 600.035714 110.661473 427.0 526.25 584.0 687.75 842.0
1000 28.0 857.000000 225.942798 595.0 711.75 806.0 916.75 1682.0
2000 30.0 1545.400000 225.239734 1191.0 1401.25 1506.0 1660.75 2251.0
3000 30.0 2701.500000 756.410113 1812.0 2274.50 2499.0 2871.50 4655.0
0.50 10 30.0 12.800000 3.527234 8.0 10.00 12.0 15.00 23.0
50 30.0 75.633333 17.974087 38.0 61.25 76.5 87.00 120.0
100 30.0 154.000000 31.289527 109.0 130.25 149.5 168.75 239.0
200 30.0 341.333333 67.102769 239.0 291.25 330.5 380.75 464.0
300 28.0 539.000000 127.809465 330.0 462.75 528.5 596.75 812.0
500 30.0 826.833333 166.162588 479.0 715.00 821.5 945.00 1087.0
700 28.0 1143.214286 246.167416 805.0 985.75 1122.0 1314.50 1907.0
1000 28.0 1726.464286 314.029779 1136.0 1543.00 1733.5 1851.00 2425.0
2000 30.0 3317.100000 531.526646 2569.0 2972.00 3181.5 3558.00 4871.0
0.75 10 30.0 25.433333 6.500309 13.0 20.25 24.0 31.00 39.0
50 30.0 171.300000 43.232451 96.0 136.50 173.5 194.00 282.0
100 30.0 356.900000 65.829115 247.0 308.75 361.0 394.50 534.0
200 30.0 806.133333 188.157075 506.0 684.00 768.5 894.75 1270.0
300 28.0 1229.821429 265.553239 779.0 1052.00 1159.5 1413.25 1760.0
500 30.0 2033.266667 466.691062 1184.0 1801.50 2009.0 2242.25 3296.0
700 28.0 2788.321429 448.442742 1862.0 2538.75 2750.5 3105.75 3813.0
1000 28.0 4065.285714 721.602633 2890.0 3634.50 4088.5 4448.00 5999.0

108 rows × 8 columns

Data displaying


In [20]:
def plotGraph(df, topology, formats, deltas, yscale="linear", xlabel="Number of robots", ylabel="", savefileBaseName=None):
    fig = plt.figure(figsize = (10,5))
    axis = fig.add_subplot(111)
    
    topologyDf = df.xs(topology, level=1)
    plotNumber=0
    for protocol in PROTOCOLS:
        for dropRate in DROP_RATES:
            currDf = topologyDf.xs((protocol, dropRate))

            numsRobots  = currDf.index.tolist()
            numsRobots  = [numsRobots[i] + deltas[plotNumber] for i in range(len(numsRobots))]
            yPlot  = currDf.xs("50%", axis=1)
            yError = [(yPlot - currDf.xs("min", axis=1)),
                      (currDf.xs("max", axis=1) - yPlot)]

            axis.errorbar(numsRobots, yPlot, yerr = yError, fmt=formats[plotNumber] + "-")
            plotNumber += 1

    axis.set_xlabel(xlabel)
    axis.set_ylabel(ylabel)
    axis.set_yscale(yscale)
    axis.yaxis.grid()
    axis.legend([str(drop*100)+"% drop" for drop in DROP_RATES], loc=0, ncol=1, title=(topology + " topology"))
    
    if savefileBaseName != None:
        plt.savefig(GRAPH_DIR+"/"+savefileBaseName+".png", dpi=600, format="png", transparent=False)

In [21]:
%matplotlib inline

# Set variables
CONSENSUS_YLABEL="Consensus Time (timesteps)"
DELTAS=[0, 0, 0, 0]
FORMATS=["ro", "go", "bo", "mo"]

# Plot graphs
plotGraph(consensusData, "line",      FORMATS, DELTAS, ylabel=CONSENSUS_YLABEL, savefileBaseName="lineConsensus")
plotGraph(consensusData, "line",      FORMATS, DELTAS, yscale="log", ylabel=CONSENSUS_YLABEL + " [log]", savefileBaseName="lineConsensus_log")
plotGraph(consensusData, "cluster",   FORMATS, DELTAS, ylabel=CONSENSUS_YLABEL, savefileBaseName="clusterConsensus")
plotGraph(consensusData, "cluster",   FORMATS, DELTAS, yscale="log", ylabel=CONSENSUS_YLABEL + " [log]", savefileBaseName="clusterConsensus_log")
plotGraph(consensusData, "scalefree", FORMATS, DELTAS, ylabel=CONSENSUS_YLABEL, savefileBaseName="scalefreeConsensus")
plotGraph(consensusData, "scalefree", FORMATS, DELTAS, yscale="log", ylabel=CONSENSUS_YLABEL + " [log]", savefileBaseName="scalefreeConsensus_log")



In [ ]: