Files @ 3e647eb7b5b3
Branch filter:

Location: AENC/switchchain/cpp/switchchain_mixingtime.cpp - annotation

Tom Bannink
Add improved construction rate dataset and plot
f7f1afb7a925
f7f1afb7a925
c9c22e41130d
be2f7fe6b220
f7f1afb7a925
f7f1afb7a925
f7f1afb7a925
f7f1afb7a925
f7f1afb7a925
f7f1afb7a925
f7f1afb7a925
f7f1afb7a925
f7f1afb7a925
1b3f095f886f
1b3f095f886f
1b3f095f886f
1b3f095f886f
f7f1afb7a925
f7f1afb7a925
f7f1afb7a925
1b3f095f886f
f7f1afb7a925
1b3f095f886f
1b3f095f886f
1b3f095f886f
1b3f095f886f
1b3f095f886f
1b3f095f886f
1b3f095f886f
1b3f095f886f
f7f1afb7a925
1b3f095f886f
1b3f095f886f
f7f1afb7a925
f7f1afb7a925
1b3f095f886f
f7f1afb7a925
f7f1afb7a925
f7f1afb7a925
f7f1afb7a925
f7f1afb7a925
f7f1afb7a925
1b3f095f886f
1b3f095f886f
1b3f095f886f
1b3f095f886f
1b3f095f886f
1b3f095f886f
1b3f095f886f
1b3f095f886f
1b3f095f886f
1b3f095f886f
1b3f095f886f
1b3f095f886f
1b3f095f886f
1b3f095f886f
1b3f095f886f
1b3f095f886f
f7f1afb7a925
f7f1afb7a925
f7f1afb7a925
1b3f095f886f
1b3f095f886f
1b3f095f886f
1b3f095f886f
1b3f095f886f
1b3f095f886f
1b3f095f886f
f7f1afb7a925
f7f1afb7a925
f7f1afb7a925
1b3f095f886f
1b3f095f886f
c9c22e41130d
c9c22e41130d
f7f1afb7a925
f7f1afb7a925
f7f1afb7a925
f7f1afb7a925
f7f1afb7a925
1b3f095f886f
f7f1afb7a925
f7f1afb7a925
f7f1afb7a925
f7f1afb7a925
1b3f095f886f
1b3f095f886f
f7f1afb7a925
f7f1afb7a925
f7f1afb7a925
f7f1afb7a925
f7f1afb7a925
f7f1afb7a925
1b3f095f886f
1b3f095f886f
f7f1afb7a925
1b3f095f886f
f7f1afb7a925
f7f1afb7a925
1b3f095f886f
f7f1afb7a925
f7f1afb7a925
f7f1afb7a925
1b3f095f886f
f7f1afb7a925
f7f1afb7a925
f7f1afb7a925
1b3f095f886f
f7f1afb7a925
f7f1afb7a925
1b3f095f886f
f7f1afb7a925
f7f1afb7a925
f7f1afb7a925
f7f1afb7a925
f7f1afb7a925
f7f1afb7a925
f7f1afb7a925
f7f1afb7a925
f7f1afb7a925
f7f1afb7a925
f7f1afb7a925
f7f1afb7a925
f7f1afb7a925
f7f1afb7a925
f7f1afb7a925
f7f1afb7a925
f7f1afb7a925
f7f1afb7a925
f7f1afb7a925
f7f1afb7a925
f7f1afb7a925
f7f1afb7a925
f7f1afb7a925
f7f1afb7a925
1b3f095f886f
1b3f095f886f
f7f1afb7a925
f7f1afb7a925
f7f1afb7a925
1b3f095f886f
f7f1afb7a925
f7f1afb7a925
f7f1afb7a925
f7f1afb7a925
f7f1afb7a925
f7f1afb7a925
f7f1afb7a925
#include "exports.hpp"
#include "graph.hpp"
#include "graph_powerlaw.hpp"
#include "switchchain.hpp"
#include <algorithm>
#include <array>
#include <fstream>
#include <iostream>
#include <numeric>
#include <random>
#include <vector>

int main(int argc, char* argv[]) {
    // Simulation parameters
    const int numVerticesMin = 1000;
    const int numVerticesMax = 4000;
    const int numVerticesStep = 500;

    float tauValues[] = {2.1f, 2.2f, 2.3f, 2.4f, 2.5f, 2.6f, 2.7f, 2.8f, 2.9f};

    const int totalDegreeSamples = 200;

    auto getMixingTime = [](int n, float tau) {
        (void)n;
        (void)tau;
        return 0;
        //return int(50.0f * (50.0f - 30.0f * (tau - 2.0f)) * n);
    };
    constexpr int measurements = 100000;
    constexpr int measureSkip = 1; // Take a sample every ... steps

    // Output file
    std::ofstream outfile;
    if (argc >= 2)
        outfile.open(argv[1]);
    else
        outfile.open("graphdata_etmt.m");
    if (!outfile.is_open()) {
        std::cout << "ERROR: Could not open output file.\n";
        return 1;
    }

    // Output Mathematica-style comment to indicate file contents
    outfile << "(*\n";
    outfile << "n from " << numVerticesMin << " to " << numVerticesMax
            << " step " << numVerticesStep << std::endl;
    outfile << "tauValues: " << tauValues << std::endl;
    outfile << "degreeSamples: " << totalDegreeSamples << std::endl;
    outfile << "mixingTime: 50 * (50 - 30 (tau - 2)) n\n";
    outfile << "data:\n";
    outfile << "1: {n,tau}\n";
    outfile << "2: avgTriangles\n";
    outfile << "3: edges\n";
    outfile << "4: etmt\n";
    outfile << "*)" << std::endl;

    // Mathematica does not accept normal scientific notation
    outfile << std::fixed;
    outfile << '{';
    bool outputComma = false;

    // Generate a random degree sequence
    std::mt19937 rng(std::random_device{}());
    Graph g;
    Graph g1;
    Graph g2;
    for (int numVertices = numVerticesMin; numVertices <= numVerticesMax;
         numVertices += numVerticesStep) {
        for (float tau : tauValues) {
            // For a single n,tau take samples over several instances of
            // the degree distribution.
            for (int degreeSample = 0; degreeSample < totalDegreeSamples;
                 ++degreeSample) {
                DegreeSequence ds;
                generatePowerlawGraph(numVertices, tau, g, ds, rng);

                // Multiple runs from the same degree sequence
                for (int i = 0; i < 5; ++i) {

                SwitchChain chain;
                if (!chain.initialize(g, true)) {
                    std::cerr << "Could not initialize Markov chain.\n";
                    return 1;
                }

                std::cout << "Running (n,tau) = (" << numVertices << ','
                          << tau << "). " << std::flush;

                int movesTotal = 0;
                int movesSuccess = 0;

                int triangles[measurements];

                // Mix
                int mixingTime = getMixingTime(numVertices, tau);
                for (int i = 0; i < mixingTime; ++i) {
                    chain.doMove();
                }

                // Measure
                for (int i = 0; i < measurements; ++i) {
                    for (int j = 0; j < measureSkip; ++j) {
                        ++movesTotal;
                        if (chain.doMove(true)) {
                            ++movesSuccess;
                        }
                    }
                    triangles[i] = chain.g.getTrackedTriangles();
                }

                std::cout << "Measuring done. " << std::flush;

                // Take the average over the last 20%
                auto trianglesTotal = 0uL;
                auto count = 0u;
                for (int i = measurements - (measurements / 5); i < measurements; ++i) {
                    trianglesTotal += triangles[i];
                    count++;
                }
                double trianglesAvg = double(trianglesTotal)/double(count);

                // Find the ETMT
                int ETMT = 0;
                for (int i = 0; i < measurements; ++i) {
                    if (triangles[i] < trianglesAvg) {
                        ETMT = i;
                        break;
                    }
                }

                if (outputComma)
                    outfile << ',' << '\n';
                outputComma = true;

                outfile << '{' << '{' << numVertices << ',' << tau << '}';
                outfile << ',' << trianglesAvg;
                outfile << ',' << g.edgeCount();
                outfile << ',' << ETMT;
                outfile << '}' << std::flush;

                std::cout << "Output done. " << std::endl;
                }
            }
        }
    }
    outfile << '}';
    return 0;
}