Cod sursa(job #1866520)

Utilizator mirupetPetcan Miruna mirupet Data 3 februarie 2017 11:15:07
Problema Xor Max Scor 0
Compilator cpp Status done
Runda Arhiva de probleme Marime 3.12 kb
#include<cstdio>
#include<cstring>
using namespace std;

FILE *fin = freopen("luffxor.in", "r", stdin);
FILE *fout = freopen("luffxor.out", "w", stdout);

int N, sol;
char S[50];
int X[32], K[32];

struct Node
{
    int noAppear;
    Node* son[2];
};

Node* emptyNode()
{
    Node* node = new Node;

    node -> son[0] = NULL;
    node -> son[1] = NULL;
    node -> noAppear = 0;

    return node;
}

void FindNumber()
{
    int len = strlen(S);
    int number = 0;

    for (int i = 2; i < len; i++)
        number = number * 10 + S[i] - '0';

    for (int i = 31; i >= 0; i--)
    {
        X[i] = number % 2;
        number /= 2;
    }
}

void FindNumbers()
{
    int len = strlen(S);
    int number = 0, i = 2;

    while (S[i] != ' ')
    {
        number = number * 10 + S[i] - '0';
        i++;
    }

    for (int i = 31; i >= 0; i--)
    {
        X[i] = number % 2;
        number /= 2;
    }

    i++; number = 0;
    while (i < len)
    {
        number = number * 10 + S[i] - '0';
        i++;
    }
    for (int i = 31; i >= 0; i--)
    {
        K[i] = number % 2;
        number /= 2;
    }
}

void recompute(Node* node)
{
    if (node == NULL)
        return;
    node -> noAppear = 0;
    if (node -> son[0] != NULL)
        node -> noAppear = node -> son[0] -> noAppear;
    if (node -> son[1])
        node -> noAppear += node -> son[1] -> noAppear;
}

void Insert(Node* node, int ind = 0)
{
    if (ind == 31)
        node -> noAppear ++;
    else
    {
        if (node -> son[X[ind]] == NULL)
            node -> son[X[ind]] = emptyNode();

        Insert(node -> son[X[ind]], ind + 1);
        recompute(node);
    }
}

void Delete(Node* node, int ind = 0)
{
    if (ind == 31)
        node -> noAppear --;
    else
    {
        if (node -> son[X[ind]] != NULL)
            node = node -> son[X[ind]];

        Delete(node, ind + 1);
        recompute(node);
    }
}

int Solve(Node* node, int ind = 0)
{
    if (ind == 31)
    {
        if (node != NULL)
            sol += node -> noAppear;
        return sol;
    }

    if (K[ind])
    {
        if (!X[ind])
        {
            sol += node -> son[0] -> noAppear;
            Solve(node -> son[1], ind + 1);
        }
        else
        {
            sol += node -> son[1] -> noAppear;
            Solve(node -> son[0], ind + 1);
        }
    }
    else
    {
        if(X[ind])
            Solve(node -> son[1], ind + 1);
        else
            Solve(node -> son[0], ind + 1);
    }
}

int main()
    {
        scanf("%d\n", &N);

        Node* root = emptyNode();

        while (N --)
        {
            gets(S);

            if (S[0] == '0')
            {
                FindNumber();
                Insert(root);
            }
            else
                if (S[0] == '1')
                {
                    FindNumber();
                    Delete(root);
                }
            else
            {
                FindNumbers(); sol = 0;
                printf("%d\n", Solve(root));
            }
        }
    }