#include <bits/stdc++.h>

using namespace std;

class Persistent_UnionFind
{
public:

    int nrComponents;

    explicit Persistent_UnionFind(){
    }

    Persistent_UnionFind(const int n, const int nr_q) : nrComponents(0), Parent(vector<int>(n + 1)), Size(vector<int>(n + 1)),
                                                        top(0), Stack(vector<pair<int,int>>(nr_q)) {
        for (int i = 1; i <= n; ++i)
            MakeSet(i);
    }

    void MakeSet(int x)
    {
        Parent[x] = x;
        Size[x] = 1;
    }

    int Find(int x) const
    {
        if (Parent[x] != x)
            return Find(Parent[x]);
        else
            return Parent[x];
    }

    void Union(int x, int y)
    {
        x = Find(x);
        y = Find(y);

        pair<int,int> operation = {-1, -1};

        if (x != y)
        {
            if (Size[x] < Size[y])
                swap(x, y);

            /// append y to x
            Size[x] += Size[y];
            Parent[y] = x;

            nrComponents--;
            operation = {x, y}; ///x-root, y-son
        }

        Stack[top++] = operation;
    }

    void disconnect(int x, int y) /// disconned y from x
    {
        if (Parent[y] == x)
        {
            Parent[y] = y;
            Size[x] -= Size[y];

            nrComponents++;
        }
    }

    void rollback()
    {
        top--;

        if (Stack[top].first != -1)
            disconnect(Stack[top].first, Stack[top].second);
    }

    bool connected(int x, int y) const
    {
        return Find(x) == Find(y);
    }

    int sizeComponent(int x) const
    {
        return Size[Find(x)];
    }

private:

    vector<int> Parent;
    vector<int> Size;

    int top;
    vector<pair<int, int>> Stack;
};

const int buffer=1<<13;
char buff[buffer]; int cnt=0;

//getInt() reads and returns one integer at a time
int getInt() {
    int number = 0;
    while(buff[cnt] < '0' || '9' < buff[cnt])
        if(++cnt >= buffer) fread(buff, buffer, 1, stdin), cnt = 0;

    while('0' <= buff[cnt] && buff[cnt] <= '9') {
        number = number * 10 + buff[cnt] - '0';
        if(++cnt >= buffer) fread(buff, buffer, 1, stdin), cnt = 0;
    }

    return number;
}

int main()
{
   // freopen("data.in", "r", stdin);

    int N, M;
    N = getInt(); M = getInt();

    Persistent_UnionFind PUF(N, M);

    while (M--)
    {
        int tip, x, y;

        tip = getInt();

        if (tip == 1)
        {
            x = getInt();
            y = getInt();

            PUF.Union(x, y);
        }
        else if (tip == 2)
        {
            x = getInt();

            while (x--)
                PUF.rollback();
        }
        else
        {
            x = getInt();
            y = getInt();

            printf("%d\n", PUF.connected(x, y));
        }
    }

    return 0;
}