在 C 中通过引用传递结构,但修改并非全部存在
Pass struct by reference in C, but modifications aren't all there
我正在尝试编写一个简单的程序来读取 C 中的配置文件。但是我的结构成员中的数据并没有保留在我放置的位置。
代码在底部。
这就是我认为我正在做的事情:
- 我正在创建一个
的结构
- 通过引用传递结构
- 从配置文件填充结构的成员
当我尝试访问成员时,我只能从配置文件的最后一行获取数据。
谢谢!
编辑:我希望它使用配置文件中的键/值填充结构。相反,它只有配置文件中最后一行的值。
预期输出
example.com
实际产量
food.txt
问题在于:
conf->key[i] = key;
conf->value[i] = value;
main.c
/*
* Goal is to make simple key value storage with struct and pointers
*/
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#define MAXLEN 100
#define CONFIG_MAX_BUF 1024
#define DELIM "="
struct config_s {
char *key[MAXLEN];
char *value[MAXLEN];
};
void read_config_file(struct config_s *conf, char *filename, int *size_of_array);
int main() {
int i = 0, size_of_array;
// type config_s has key and value members
struct config_s c;
read_config_file(&c, "test.cfg", &size_of_array);
printf("size of array: %i\n", size_of_array);
// if i want to print them all out, i can use this, but i'll have
// a function to search for a certain key and return the value.
int l = 0, e = 1;
printf("********** TEST 1 ***********\n");
printf("key: [%s] value: [%s] i: [%i]\n", c.key[l], c.value[l], l);
printf("key: [%s] value: [%s] i: [%i]\n", c.key[e], c.value[e], e);
printf("********** TEST 2 ***********\n");
return 0;
}
void read_config_file(struct config_s *conf, char *filename, int *size_of_array) {
FILE *file;
file = fopen(filename, "r");
char line[CONFIG_MAX_BUF];
int i = 0;
char *cfline;
char *key;
char *value;
while(fgets(line, sizeof(line), file) != NULL) {
cfline = strstr((char *)line, DELIM);
value = cfline + strlen(DELIM);
value[strlen(value) - 1] = '[=11=]';
key = strtok((char *)line, DELIM);
printf("%i %s %s\n", i, key, value);
conf->key[i] = key;
conf->value[i] = value;
printf("%i %s %s\n", i, (*conf).key[i], (*conf).value[i]);
i++;
}
printf("%s %s\n", (*conf).key[0], (*conf).value[0]);
fclose(file);
*size_of_array = i;
return;
}
test.cfg
server=example.com
port=443
file=food.txt
您的代码中可能存在不止一个问题。我可以在 get_value_by_key
函数中看到其中一个。在这里,您将 conf->key[i]
与 key
进行比较,这永远不会是真的(因为您正在比较两个不同的指针)。相反,您想要做的是:
if(strncmp(conf->key[i], key, strlen(conf->key[i])+1) == 0)
比较这两个指针指向的两个字符串。
char *get_value_by_key(config_s *conf, char *key, int config_size) {
int i;
for(i=0;i<config_size;i++) {
/*if(conf->key[i] == key) {*/ //Instead of this
/* Do this */
if(strncmp(conf->key[i], key, strlen(conf->key[i])+1) == 0) {
return conf->value[i];
}
}
/* Also return NULL if there is no match */
return NULL;
}
在您最新版本的 read_config_file
中,您正在保存指向指向 的值的指针 缓冲区 line
,位于 stack,所以这些指针将在return.
时失效
即使缓冲区是全局的,每一行的指针也会相互冲突,因为每次 fgets
调用都会覆盖缓冲区。
变化:
conf->key[i] = key;
conf->value[i] = value;
进入:
conf->key[i] = strdup(key);
conf->value[i] = strdup(value);
我正在尝试编写一个简单的程序来读取 C 中的配置文件。但是我的结构成员中的数据并没有保留在我放置的位置。
代码在底部。
这就是我认为我正在做的事情:
- 我正在创建一个 的结构
- 通过引用传递结构
- 从配置文件填充结构的成员
当我尝试访问成员时,我只能从配置文件的最后一行获取数据。
谢谢!
编辑:我希望它使用配置文件中的键/值填充结构。相反,它只有配置文件中最后一行的值。
预期输出
example.com
实际产量
food.txt
问题在于:
conf->key[i] = key;
conf->value[i] = value;
main.c
/*
* Goal is to make simple key value storage with struct and pointers
*/
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#define MAXLEN 100
#define CONFIG_MAX_BUF 1024
#define DELIM "="
struct config_s {
char *key[MAXLEN];
char *value[MAXLEN];
};
void read_config_file(struct config_s *conf, char *filename, int *size_of_array);
int main() {
int i = 0, size_of_array;
// type config_s has key and value members
struct config_s c;
read_config_file(&c, "test.cfg", &size_of_array);
printf("size of array: %i\n", size_of_array);
// if i want to print them all out, i can use this, but i'll have
// a function to search for a certain key and return the value.
int l = 0, e = 1;
printf("********** TEST 1 ***********\n");
printf("key: [%s] value: [%s] i: [%i]\n", c.key[l], c.value[l], l);
printf("key: [%s] value: [%s] i: [%i]\n", c.key[e], c.value[e], e);
printf("********** TEST 2 ***********\n");
return 0;
}
void read_config_file(struct config_s *conf, char *filename, int *size_of_array) {
FILE *file;
file = fopen(filename, "r");
char line[CONFIG_MAX_BUF];
int i = 0;
char *cfline;
char *key;
char *value;
while(fgets(line, sizeof(line), file) != NULL) {
cfline = strstr((char *)line, DELIM);
value = cfline + strlen(DELIM);
value[strlen(value) - 1] = '[=11=]';
key = strtok((char *)line, DELIM);
printf("%i %s %s\n", i, key, value);
conf->key[i] = key;
conf->value[i] = value;
printf("%i %s %s\n", i, (*conf).key[i], (*conf).value[i]);
i++;
}
printf("%s %s\n", (*conf).key[0], (*conf).value[0]);
fclose(file);
*size_of_array = i;
return;
}
test.cfg
server=example.com
port=443
file=food.txt
您的代码中可能存在不止一个问题。我可以在 get_value_by_key
函数中看到其中一个。在这里,您将 conf->key[i]
与 key
进行比较,这永远不会是真的(因为您正在比较两个不同的指针)。相反,您想要做的是:
if(strncmp(conf->key[i], key, strlen(conf->key[i])+1) == 0)
比较这两个指针指向的两个字符串。
char *get_value_by_key(config_s *conf, char *key, int config_size) {
int i;
for(i=0;i<config_size;i++) {
/*if(conf->key[i] == key) {*/ //Instead of this
/* Do this */
if(strncmp(conf->key[i], key, strlen(conf->key[i])+1) == 0) {
return conf->value[i];
}
}
/* Also return NULL if there is no match */
return NULL;
}
在您最新版本的 read_config_file
中,您正在保存指向指向 的值的指针 缓冲区 line
,位于 stack,所以这些指针将在return.
即使缓冲区是全局的,每一行的指针也会相互冲突,因为每次 fgets
调用都会覆盖缓冲区。
变化:
conf->key[i] = key;
conf->value[i] = value;
进入:
conf->key[i] = strdup(key);
conf->value[i] = strdup(value);