所以这个函数(tmap_insert)正在做一些好奇的事情。我在一个循环中调用它,并且出于某种原因,每当我添加一个新项目时,它会覆盖树中所有先前添加的项目的item-> name(但不是item-> val!),给它最近添加的名称。我已经在这里发布了我的代码供您查看 - 它已经很长了但是我无能为力。
另外,我已经包含了相关的结构,以及在循环中调用它的函数。
int tmap_insert(TMAP_PTR t, char * name, double val){
TMAP_PTR parent = malloc(sizeof(struct tmap_struct));
TMAP_PTR new = malloc(sizeof(struct tmap_struct));
NAME_VAL* temp = malloc(sizeof(NAME_VAL));
temp->name = name;
temp->value = val;
new->item = temp;
new->size = 1;
new->height = 0;
while (t != NULL)
{
t->size = t->size + 1;
if (val > (t->item)->value)
{
parent = t;
t = t->right;
}
else if (val < (t->item)->value)
{
parent = t;
t = t->left;
}
}
if (parent != NULL)
{
new->parent = parent;
if (val > (parent->item)->value)
{
parent->right = new;
}
else if (val < (parent->item)->value)
{
parent->left = new;
}
}
TMAP_PTR unbalanced = malloc(sizeof(struct tmap_struct));
unbalanced = NULL;
TMAP_PTR iterator = malloc(sizeof(struct tmap_struct));
iterator = new->parent;
while (iterator != NULL)
{
if (iterator->left != NULL && iterator->right != NULL)
{
if ((iterator->left)->size > (2*((iterator->right)->size) + 1) || (iterator->right)->size > (2*((iterator->left)->size) + 1))
{
unbalanced = iterator;
}
if ((iterator->left)->height > (iterator->right)->height)
{
iterator->height = (iterator->left)->height + 1;
}
else
{
iterator->height = (iterator->right)->height + 1;
}
}
else if (iterator->left != NULL)
{
if ((iterator->left)->size > 1)
{
unbalanced = iterator;
}
iterator->height = (iterator->left)->height + 1;
}
else
{
if ((iterator->right)->size > 1)
{
unbalanced = iterator;
}
iterator->height = (iterator->right)->height + 1;
}
iterator = iterator->parent;
}
if (unbalanced != NULL)
{
NAME_VAL **arr = malloc(unbalanced->size * sizeof(NAME_VAL*));
int i;
for (i = 0; i < unbalanced->size; i++)
{
arr[i] = malloc(sizeof(NAME_VAL));
}
int *index = malloc(sizeof(int));
*index = 0;
arr = make_arr(unbalanced, arr, index);
int pos = ((unbalanced->size) / 2);
TMAP_PTR head = malloc(sizeof(struct tmap_struct));
head->size = 1;
head->height = 0;
head->item = arr[pos];
rebalance(arr, 0, pos-1, head);
rebalance(arr, pos+1, unbalanced->size, head);
unbalanced->parent = head->parent;
if ((unbalanced->parent)->right == unbalanced)
{
(unbalanced->parent)->right = head;
}
else
{
(unbalanced->parent)->left = head;
}
}
return 1;
}
TMAP_PTR tmap_create(char *fname){
printf("%s", fname);
fflush(stdout);
FILE *src;
src = fopen(fname, "r");
if (src == NULL)
{
printf("File could not open!\n");
return;
}
double value;
char name[20];
TMAP_PTR head = malloc(sizeof(struct tmap_struct));
head->size = 1;
head->height = 0;
fscanf(src, "%s", name);
fscanf(src, "%lf", &value);
head->item = malloc(sizeof(NAME_VAL));
(head->item)->value = value;
(head->item)->name = name;
while (fscanf(src, "%s %lf", name, &value) == 2)
{
printf("%s", name);
fflush(stdout);
tmap_insert(head, name, value);
}
return head;
}
struct tmap_struct{
TMAP_PTR parent;
TMAP_PTR left;
TMAP_PTR right;
int height;
int size;
NAME_VAL* item;
};
typedef struct name_val {
char *name;
double value;
}NAME_VAL;
答案 0 :(得分:0)
在tmap_create(char *fname)
中为name分配一个char数组,然后在循环的每一步中读入name的新值,并将其传递给函数tmap_insert,在那里创建一个新节点,在其中存储指向char数组的指针。显然,树的所有节点都指向同一个char数组,当你在其中存储一个新字符串时,所有节点都会看到新值。解决方案是为您必须存储的每个名称分配一个新的char数组。
您应该使用:
char* name = malloc(20*sizeof(char));
while (fscanf(src, "%s %lf", name, &value) == 2)
{
printf("%s", name);
fflush(stdout);
tmap_insert(head, name, value);
name = malloc(20*sizeof(char));
}