Quanto è il limite? Quanto hai usato finora?
Poi rimetti il codice aggiornato nella versione che serve a nippolo, altrimenti non può aiutarti…
Tipo così
#include <stdio.h>
#include <stdlib.h>
#include <stdint.h>
#include <string.h>
#define N 123
FILE * fp, * out;
typedef struct node_ {
char* key;
struct node_* left;
struct node_* right;
} node;
typedef struct nodo_ {
node *n;
char *res;
uint8_t SI[N];
uint8_t NO[N];
uint8_t *u;
uint8_t u_dim;
struct nodo_ *next;
} nodo;
typedef struct pnode_ {
node *n;
struct pnode_ *next;
} pnode;
int strcmp(const char *s1, const char *s2) {
while (*s1 && (*s1 == *s2)) {
s1++;
s2++;
}
return (*(const unsigned char*)s1 - *(const unsigned char*)s2);
}
node* tree_search(node **root, char *word) {
int val;
while (*root != NULL) {
if (!(val = strcmp((*root)->key, word))) {
return (*root);
} else if (val < 0) {
root = &(*root)->right;
} else {
root = &(*root)->left;
}
}
return (NULL);
}
void tree_insert(node **root, node *n) {
while (*root != NULL) {
if (strcmp((*root)->key, n->key) < 0) {
root = &(*root)->right;
} else {
root = &(*root)->left;
}
}
*root = n;
}
void print_filtered(pnode **comp_w) {
while (*comp_w != NULL) {
fprintf(out, "%s\n", (*comp_w)->n->key);
comp_w = &(*comp_w)->next;
}
}
int end_game(node **root, unsigned int l, node *n, char *i) {
while (1) {
if (EOF == fscanf(fp, "%s", i)) {
return (0);
}
if (!strcmp(i, "+nuova_partita")) {
return (1);
} else {
while (1) {
if (EOF == fscanf(fp, "%s", i)) {
return (0);
}
if (!strcmp(i, "+inserisci_fine")) {
break;
} else {
n = calloc(1, sizeof(node) + sizeof(char) * (l + 1));
n->key = (char*) n + sizeof(node);
strcpy(n->key, i);
n->left = NULL;
n->right = NULL;
tree_insert(root, n);
}
}
}
}
}
void pnode_insert(pnode **pn, node *n, pnode *new) {
new = (pnode*)calloc(1, sizeof(pnode));
new->n = n;
new->next = *pn;
*pn = new;
}
void comp_free(pnode **comp_w) {
pnode *del;
while (*comp_w != NULL) {
del = *comp_w;
*comp_w = (*comp_w)->next;
free(del);
}
}
void comp_reset(node **root, pnode **comp_w, pnode *new, unsigned int *m) {
if (*root != NULL) {
++*m;
comp_reset(&(*root)->right, comp_w, new, m);
pnode_insert(comp_w, *root, new);
comp_reset(&(*root)->left, comp_w, new, m);
}
}
void list_reset(nodo **c_list) {
nodo *del;
while (*c_list != NULL) {
del = *c_list;
*c_list = (*c_list)->next;
free(del);
}
}
nodo* add_comparison(nodo **c_list, node *a, uint8_t l) {
while (*c_list != NULL) {
c_list = &(*c_list)->next;
}
*c_list = calloc(1, sizeof(nodo) + sizeof(char) * (l + 1) + sizeof(uint8_t) * l);
(*c_list)->n = a;
(*c_list)->next = NULL;
(*c_list)->res = (char*) *c_list + sizeof(nodo);
(*c_list)->u = (uint8_t*) *c_list + sizeof(nodo) + sizeof(char) * (l + 1);
(*c_list)->res[l] = '\0';
return (*c_list);
}
nodo* calculate_comparison(nodo *n, const char *k) {
memset(n->SI, (int)(n->u_dim = 0), sizeof(*n->SI) * N);
memset(n->NO, 0, sizeof(*n->NO) * N);
uint8_t v[N] = {0};
for(unsigned int i = 0; k[i]; ++i)
{
if(n->n->key[i] == k[i])
{
n->res[i] = '+';
}
else
{
n->res[i] = '/';
++v[(int)k[i]];
}
}
for(unsigned int i = 0; k[i]; ++i)
{
if(n->res[i] == '/')
{
if(v[(int)n->n->key[i]])
{
n->res[i] = '|';
--v[(int)n->n->key[i]];
if(!n->SI[(int)n->n->key[i]]++)
{
n->u[(n->u_dim)++] = n->n->key[i];
}
}
else
{
++n->NO[(int)n->n->key[i]];
}
}
}
return (n);
}
int is_compatible(const char *p, nodo *n) {
uint8_t v[N] = {0};
unsigned int i;
for(i = 0; n->n->key[i] && (n->res[i] == '+' ? p[i] == n->n->key[i] : p[i] != n->n->key[i] && ++v[(int)p[i]] && (!n->NO[(int)(p[i])] || n->SI[(int)(p[i])] - v[(int)(p[i])] >= 0)); ++i);
for(i = !n->n->key[i] ? 0 : n->u_dim + 1; i < n->u_dim && v[n->u[i]] - n->SI[n->u[i]] >= 0; ++i);
return(i == n->u_dim);
}
void update_compatibilities(pnode **comp_w, nodo *n1, unsigned int *m) {
pnode *del;
while (*comp_w != NULL) {
if (!is_compatible((*comp_w)->n->key, n1)) {
del = *comp_w;
*comp_w = (*comp_w)->next;
free(del);
--*m;
} else {
comp_w = &(*comp_w)->next;
}
}
}
int respect_constraints(nodo **p, char *i) {
while (*p != NULL) {
if (!is_compatible(i, *p)) {
return (0);
}
p = &(*p)->next;
}
return (1);
}
void pnode_insert_in_order(pnode **comp_w, node *n) {
pnode *new;
while (*comp_w != NULL && strcmp((*comp_w)->n->key, n->key) < 0) {
comp_w = &(*comp_w)->next;
}
new = (pnode*)calloc(1, sizeof(pnode));
new->n = n;
new->next = *comp_w;
*comp_w = new;
}
void build_compatible_words(node **el_w, pnode **comp_w, pnode *new) {
if (*el_w != NULL) {
build_compatible_words(&(*el_w)->right, comp_w, new);
pnode_insert(comp_w, *el_w, new);
build_compatible_words(&(*el_w)->left, comp_w, new);
}
}
int main() {
node *eligible_words = NULL;
nodo *comparison_list = NULL, *temp;
node *new_node = NULL;
pnode *compatible_words = NULL, *new = NULL;
char input[100], *key;
uint8_t length;
unsigned int num_comp = 0, rounds;
if ((fp=fopen("test3.txt", "r"))==NULL)
return -1;
if ((out=fopen("out.txt", "w"))==NULL)
return -2;
if (EOF == fscanf(fp, "%s", &length)) {
return (0);
}
while (1) {
if (EOF == fscanf(fp, "%s", input)) {
return (0);
}
if (!strcmp(input, "+nuova_partita")) {
break;
} else {
new_node = calloc(1, sizeof(node) + sizeof(char) * (length + 1));
new_node->key = (char*) new_node + sizeof(node);
new_node->left = NULL;
new_node->right = NULL;
strcpy(new_node->key, input);
++num_comp;
tree_insert(&eligible_words, new_node);
}
}
build_compatible_words(&eligible_words, &compatible_words, new);
key = (char*)calloc(1, sizeof(char) * (length + 1));
while (1) {
if (EOF == fscanf(fp,"%s", key) || EOF == fscanf(fp,"%d", &rounds)) {
break;
}
while (1) {
if (EOF == fscanf(fp, "%s", input)) {
return (0);
}
if (input[0] != '+') {
if (!strcmp(input, key)) {
fprintf(out, "ok\n");
if (!end_game(&eligible_words, length, new_node, input)) {
fclose(out);
fclose(fp);
return (0);
}
num_comp = 0;
comp_free(&compatible_words);
comp_reset(&eligible_words, &compatible_words, new, &num_comp);
list_reset(&comparison_list);
break;
} else if ((new_node = tree_search(&eligible_words, input)) != NULL) {
update_compatibilities(&compatible_words, calculate_comparison(temp = add_comparison(&comparison_list, new_node, length), key), &num_comp);
fprintf(out, "%s\n%u\n", temp->res, num_comp);
if (!(--rounds)) {
fprintf(out, "ko\n");
if (!end_game(&eligible_words, length, new_node, input)) {
return (0);
}
num_comp = 0;
comp_free(&compatible_words);
comp_reset(&eligible_words, &compatible_words, new, &num_comp);
list_reset(&comparison_list);
break;
}
} else {
fprintf(out, "not_exists\n");
}
} else if (!strcmp(input, "+stampa_filtrate")) {
print_filtered(&compatible_words);
} else if (!strcmp(input, "+inserisci_inizio")) {
while (1) {
if (EOF == fscanf(fp, "%s", input)) {
return (0);
}
if (!strcmp(input, "+inserisci_fine")) {
break;
} else {
new_node = calloc(1, sizeof(node) + sizeof(char) * (length + 1));
new_node->key = (char*) new_node + sizeof(node);
new_node->left = NULL;
new_node->right = NULL;
strcpy(new_node->key, input);
if (respect_constraints(&comparison_list, input)) {
++num_comp;
pnode_insert_in_order(&compatible_words, new_node);
}
tree_insert(&eligible_words, new_node);
}
}
} else if (!strcmp(input, "+nuova_partita")) {
num_comp = 0;
comp_free(&compatible_words);
comp_reset(&eligible_words, &compatible_words, new, &num_comp);
list_reset(&comparison_list);
break;
} else {
fclose(out);
fclose(fp);
return (0);
}
}
}
fclose(out);
fclose(fp);
return (0);
}