Cod sursa(job #1714268)

Utilizator Andrei1998Andrei Constantinescu Andrei1998 Data 7 iunie 2016 21:33:40
Problema Robo Scor 0
Compilator cpp Status done
Runda Arhiva ICPC Marime 2.6 kb
#include <fstream>
#include <algorithm>
#include <vector>
#include <string>
#include <cstring>
#include <sstream>

using namespace std;

const int NMAX = 5200;
const int SIGMAMAX = 10;

class Automaton {
public:
    Automaton(int n, int sigma, int q0 = 0): N(n), SIGMA(sigma), Q0(q0) {}

    void add_final_state(int node) {
        f.push_back(node);
    }

    void add_transition(int node1, char c, int node2) {
        trans[node1][c - 'a'] = node2;
    }

    int minimize() {
        //Set labels according to accepting states
        memset(labels, 0, sizeof labels);
        for (auto it: f)
            labels[it] = 1;

        int labels_count_init = 0;
        while (1) {
            for (int i = 0; i < N; ++ i)
                labels_count_init = max(labels_count_init, labels[i]);

            //Built auxiliary transition table
            for (int i = 0; i < N; ++ i) {
                sortable_table[i].first.resize(N);
                sortable_table[i].second = i;

                for (int j = 0; j < SIGMA;  ++ j) {
                    table[i][j] = labels[trans[i][j]];
                    sortable_table[i].first[j] = table[i][j];
                }
            }

            //Sort the table
            sort(sortable_table, sortable_table + N);

            //Relabel
            int label = 0;
            for (int i = 0; i < N; ++ i) {
                if (!i || sortable_table[i].first != sortable_table[i - 1].first)
                    ++ label;
                labels[sortable_table[i].second] = label;
            }

            if (labels_count_init == label)
                break;
        }

        return labels_count_init;
    }
private:
    const int N;
    const int SIGMA;
    const int Q0;

    vector <int> f;

    int trans[NMAX][SIGMAMAX];

    int table[NMAX][SIGMAMAX];
    int labels[NMAX];

    pair <vector <int>, int> sortable_table[NMAX];
};

int main()
{
    ifstream cin("robo.in");
    ofstream cout("robo.out");

    int t = 0;
    cin >> t;

    while (t --) {
        int n, sigma;
        cin >> n >> sigma; cin.ignore();

        Automaton aut(n, sigma);

        string str;
        getline(cin, str);
        stringstream ss(str + " ");

        int node;
        while (ss >> node)
            aut.add_final_state(node);

        int a, b;
        char c;
        for (int i = 0; i < n * sigma; ++ i) {
            cin >> a >> c >> b;
            aut.add_transition(a, c, b);
        }

        cout << aut.minimize() << '\n';
    }

    cin.close();
    cout.close();
    return 0;
}