Pagini recente » Cod sursa (job #2540298) | Cod sursa (job #3359769) | Cod sursa (job #3359774) | Cod sursa (job #3359775)
#include <cstdio>
#include <vector>
#include <cstdint>
#include <cctype>
// --- PARSER PENTRU CITIRE RAPIDA ---
class InParser {
private:
FILE *fin;
char *buff;
int sp;
const int SIZE = 65536; // 64KB
inline char read_ch() {
if (sp == SIZE) {
fread(buff, 1, SIZE, fin);
sp = 0;
}
return buff[sp++];
}
public:
InParser(const char* nume) {
fin = fopen(nume, "r");
buff = new char[SIZE];
sp = SIZE;
}
~InParser() {
delete[] buff;
if (fin) fclose(fin);
}
InParser& operator >> (int &n) {
char c;
while (!isdigit(c = read_ch()));
n = c - '0';
while (isdigit(c = read_ch())) {
n = 10 * n + c - '0';
}
return *this;
}
};
// --- PARSER PENTRU SCRIERE RAPIDA ---
class OutParser {
private:
FILE *fout;
char *buff;
int sp;
const int SIZE = 65536;
public:
OutParser(const char* nume) {
fout = fopen(nume, "w");
buff = new char[SIZE];
sp = 0;
}
~OutParser() {
if (sp > 0) fwrite(buff, 1, sp, fout);
delete[] buff;
if (fout) fclose(fout);
}
OutParser& operator << (char c) {
if (sp == SIZE) {
fwrite(buff, 1, SIZE, fout);
sp = 0;
}
buff[sp++] = c;
return *this;
}
};
// --- HASH TABLE OPTIMIZAT PENTRU SET ---
class HashTable
{
private:
int HASH_SIZE;
std::vector<int> head;
struct Node
{
int key;
int next;
};
std::vector<Node> nodes;
std::vector<int> free_list;
int node_count;
static constexpr int HASH_BITS = 20;
inline int get_hash(int x) const
{
uint32_t h = static_cast<uint32_t>(x) * 2654435769u;
return h >> (32 - HASH_BITS);
}
public:
HashTable(int max_elements = 1000005)
{
HASH_SIZE = 1 << HASH_BITS;
head.assign(HASH_SIZE, -1);
nodes.resize(max_elements);
free_list.reserve(max_elements);
node_count = 0;
}
inline int allocate_node()
{
if (!free_list.empty())
{
int recycled_index = free_list.back();
free_list.pop_back();
return recycled_index;
}
return node_count++;
}
void Insert(int x)
{
int h = get_hash(x);
for (int i = head[h]; i != -1; i = nodes[i].next)
{
if (nodes[i].key == x)
return; // Elementul exista deja in set, nu facem nimic
}
int new_idx = allocate_node();
nodes[new_idx].key = x;
nodes[new_idx].next = head[h];
head[h] = new_idx;
}
void Delete(int x)
{
int h = get_hash(x);
int prev = -1;
for (int i = head[h]; i != -1; prev = i, i = nodes[i].next)
{
if (nodes[i].key == x)
{
if (prev == -1) head[h] = nodes[i].next;
else nodes[prev].next = nodes[i].next;
free_list.push_back(i); // Reciclam nodul
return;
}
}
}
bool Find(int x) const
{
int h = get_hash(x);
for (int i = head[h]; i != -1; i = nodes[i].next)
{
if (nodes[i].key == x) return true;
}
return false;
}
};
int main()
{
InParser fin("hashuri.in");
OutParser fout("hashuri.out");
HashTable A;
int n{}, x{}, y{};
fin >> n;
for(int i = 0; i < n; i++)
{
fin >> x >> y;
if(x == 1) A.Insert(y);
else if(x == 2) A.Delete(y);
else
{
fout << (A.Find(y) ? '1' : '0');
fout << '\n';
}
}
return 0;
}