#include <stdio.h>
#include <stdlib.h>
#define MAX_BITS 32
// Trie node structure
typedef struct TrieNode {
struct TrieNode *children[2]; // Left (0) and Right (1)
int match;
int prefix_length;
} TrieNode;
// Root of the Trie
TrieNode *root;
// Convert an IP address to a 32-bit integer
unsigned int ip(int a, int b, int c, int d) {
return (a << 24) | (b << 16) | (c << 8) | d;
}
// Create a new Trie node
TrieNode *newTrieNode() {
TrieNode
*node
= (TrieNode
*)malloc(sizeof(TrieNode
)); node->children[0] = node->children[1] = NULL;
node->match = -1; // Default match value
node->prefix_length = -1; // No prefix set initially
return node;
}
// Insert subnet into the Trie
void insertSubnet(int a, int b, int c, int d, int bits, int match) {
unsigned int subnet = ip(a, b, c, d);
TrieNode *current = root;
for (int i = 31; i >= 32 - bits; i--) {
int bit = (subnet >> i) & 1; // Extract i-th bit
if (!current->children[bit]) {
current->children[bit] = newTrieNode();
}
current = current->children[bit];
}
// Store the match value and prefix length
current->match = match;
current->prefix_length = bits;
}
// Search for the best match for a given IP
int searchIP(int a, int b, int c, int d) {
unsigned int target = ip(a, b, c, d);
TrieNode *current = root;
int best_match = -1;
int longest_prefix = -1;
for (int i = 31; i >= 0; i--) {
int bit = (target >> i) & 1;
if (!current->children[bit]) {
break; // No more matching bits
}
current = current->children[bit];
if (current->prefix_length != -1) { // Valid match found
best_match = current->match;
longest_prefix = current->prefix_length;
}
}
return best_match;
}
// Free Trie memory
void freeTrie(TrieNode *node) {
if (!node)
return;
freeTrie(node->children[0]);
freeTrie(node->children[1]);
}
int main() {
int n, m;
root = newTrieNode(); // Initialize Trie root
// Read and insert subnets into the Trie
for (int i = 0; i < n; i++) {
int a, b, c, d, bits, match;
scanf("%d.%d.%d.%d/%d %d", &a
, &b
, &c
, &d
, &bits
, &match
); insertSubnet(a, b, c, d, bits, match);
}
// Read and process IPs
for (int i = 0; i < m; i++) {
int a, b, c, d;
scanf("%d.%d.%d.%d", &a
, &b
, &c
, &d
); printf("%d\n", searchIP
(a
, b
, c
, d
)); }
freeTrie(root); // Free memory
return 0;
}
I2luY2x1ZGUgPHN0ZGlvLmg+CiNpbmNsdWRlIDxzdGRsaWIuaD4KCiNkZWZpbmUgTUFYX0JJVFMgMzIKCi8vIFRyaWUgbm9kZSBzdHJ1Y3R1cmUKdHlwZWRlZiBzdHJ1Y3QgVHJpZU5vZGUgewogIHN0cnVjdCBUcmllTm9kZSAqY2hpbGRyZW5bMl07IC8vIExlZnQgKDApIGFuZCBSaWdodCAoMSkKICBpbnQgbWF0Y2g7CiAgaW50IHByZWZpeF9sZW5ndGg7Cn0gVHJpZU5vZGU7CgovLyBSb290IG9mIHRoZSBUcmllClRyaWVOb2RlICpyb290OwoKLy8gQ29udmVydCBhbiBJUCBhZGRyZXNzIHRvIGEgMzItYml0IGludGVnZXIKdW5zaWduZWQgaW50IGlwKGludCBhLCBpbnQgYiwgaW50IGMsIGludCBkKSB7CiAgcmV0dXJuIChhIDw8IDI0KSB8IChiIDw8IDE2KSB8IChjIDw8IDgpIHwgZDsKfQoKLy8gQ3JlYXRlIGEgbmV3IFRyaWUgbm9kZQpUcmllTm9kZSAqbmV3VHJpZU5vZGUoKSB7CiAgVHJpZU5vZGUgKm5vZGUgPSAoVHJpZU5vZGUgKiltYWxsb2Moc2l6ZW9mKFRyaWVOb2RlKSk7CiAgbm9kZS0+Y2hpbGRyZW5bMF0gPSBub2RlLT5jaGlsZHJlblsxXSA9IE5VTEw7CiAgbm9kZS0+bWF0Y2ggPSAtMTsgICAgICAgICAvLyBEZWZhdWx0IG1hdGNoIHZhbHVlCiAgbm9kZS0+cHJlZml4X2xlbmd0aCA9IC0xOyAvLyBObyBwcmVmaXggc2V0IGluaXRpYWxseQogIHJldHVybiBub2RlOwp9CgovLyBJbnNlcnQgc3VibmV0IGludG8gdGhlIFRyaWUKdm9pZCBpbnNlcnRTdWJuZXQoaW50IGEsIGludCBiLCBpbnQgYywgaW50IGQsIGludCBiaXRzLCBpbnQgbWF0Y2gpIHsKICB1bnNpZ25lZCBpbnQgc3VibmV0ID0gaXAoYSwgYiwgYywgZCk7CiAgVHJpZU5vZGUgKmN1cnJlbnQgPSByb290OwoKICBmb3IgKGludCBpID0gMzE7IGkgPj0gMzIgLSBiaXRzOyBpLS0pIHsKICAgIGludCBiaXQgPSAoc3VibmV0ID4+IGkpICYgMTsgLy8gRXh0cmFjdCBpLXRoIGJpdAogICAgaWYgKCFjdXJyZW50LT5jaGlsZHJlbltiaXRdKSB7CiAgICAgIGN1cnJlbnQtPmNoaWxkcmVuW2JpdF0gPSBuZXdUcmllTm9kZSgpOwogICAgfQogICAgY3VycmVudCA9IGN1cnJlbnQtPmNoaWxkcmVuW2JpdF07CiAgfQogIC8vIFN0b3JlIHRoZSBtYXRjaCB2YWx1ZSBhbmQgcHJlZml4IGxlbmd0aAogIGN1cnJlbnQtPm1hdGNoID0gbWF0Y2g7CiAgY3VycmVudC0+cHJlZml4X2xlbmd0aCA9IGJpdHM7Cn0KCi8vIFNlYXJjaCBmb3IgdGhlIGJlc3QgbWF0Y2ggZm9yIGEgZ2l2ZW4gSVAKaW50IHNlYXJjaElQKGludCBhLCBpbnQgYiwgaW50IGMsIGludCBkKSB7CiAgdW5zaWduZWQgaW50IHRhcmdldCA9IGlwKGEsIGIsIGMsIGQpOwogIFRyaWVOb2RlICpjdXJyZW50ID0gcm9vdDsKCiAgaW50IGJlc3RfbWF0Y2ggPSAtMTsKICBpbnQgbG9uZ2VzdF9wcmVmaXggPSAtMTsKCiAgZm9yIChpbnQgaSA9IDMxOyBpID49IDA7IGktLSkgewogICAgaW50IGJpdCA9ICh0YXJnZXQgPj4gaSkgJiAxOwogICAgaWYgKCFjdXJyZW50LT5jaGlsZHJlbltiaXRdKSB7CiAgICAgIGJyZWFrOyAvLyBObyBtb3JlIG1hdGNoaW5nIGJpdHMKICAgIH0KICAgIGN1cnJlbnQgPSBjdXJyZW50LT5jaGlsZHJlbltiaXRdOwogICAgaWYgKGN1cnJlbnQtPnByZWZpeF9sZW5ndGggIT0gLTEpIHsgLy8gVmFsaWQgbWF0Y2ggZm91bmQKICAgICAgYmVzdF9tYXRjaCA9IGN1cnJlbnQtPm1hdGNoOwogICAgICBsb25nZXN0X3ByZWZpeCA9IGN1cnJlbnQtPnByZWZpeF9sZW5ndGg7CiAgICB9CiAgfQoKICByZXR1cm4gYmVzdF9tYXRjaDsKfQoKLy8gRnJlZSBUcmllIG1lbW9yeQp2b2lkIGZyZWVUcmllKFRyaWVOb2RlICpub2RlKSB7CiAgaWYgKCFub2RlKQogICAgcmV0dXJuOwogIGZyZWVUcmllKG5vZGUtPmNoaWxkcmVuWzBdKTsKICBmcmVlVHJpZShub2RlLT5jaGlsZHJlblsxXSk7CiAgZnJlZShub2RlKTsKfQoKaW50IG1haW4oKSB7CiAgaW50IG4sIG07CiAgc2NhbmYoIiVkIiwgJm4pOwoKICByb290ID0gbmV3VHJpZU5vZGUoKTsgLy8gSW5pdGlhbGl6ZSBUcmllIHJvb3QKCiAgLy8gUmVhZCBhbmQgaW5zZXJ0IHN1Ym5ldHMgaW50byB0aGUgVHJpZQogIGZvciAoaW50IGkgPSAwOyBpIDwgbjsgaSsrKSB7CiAgICBpbnQgYSwgYiwgYywgZCwgYml0cywgbWF0Y2g7CiAgICBzY2FuZigiJWQuJWQuJWQuJWQvJWQgJWQiLCAmYSwgJmIsICZjLCAmZCwgJmJpdHMsICZtYXRjaCk7CiAgICBpbnNlcnRTdWJuZXQoYSwgYiwgYywgZCwgYml0cywgbWF0Y2gpOwogIH0KCiAgLy8gUmVhZCBhbmQgcHJvY2VzcyBJUHMKICBzY2FuZigiJWQiLCAmbSk7CiAgZm9yIChpbnQgaSA9IDA7IGkgPCBtOyBpKyspIHsKICAgIGludCBhLCBiLCBjLCBkOwogICAgc2NhbmYoIiVkLiVkLiVkLiVkIiwgJmEsICZiLCAmYywgJmQpOwogICAgcHJpbnRmKCIlZFxuIiwgc2VhcmNoSVAoYSwgYiwgYywgZCkpOwogIH0KCiAgZnJlZVRyaWUocm9vdCk7IC8vIEZyZWUgbWVtb3J5CiAgcmV0dXJuIDA7Cn0=