0

例如,我有这个块:

int nFirst, nSecond;
char sInput[10];
printf("Which variable to change to 10?");
scanf("%s", &sInput);
// BAD - inflexible and unmaintainable
if(strcmp(sInput,"nFirst") ==0){
    nFirst = 10;
}
else if (strcmp(sInput,"nSecond")==0) {
    nSecond =10;
}

有没有很好的方法来做到这一点?就像将字符串视为变量名一样?

4

5 回答 5

1

不,在 C 中没有“好”的方式来执行此操作。变量名称(通常)不会保留在生成的机器代码中,除了支持调试。C 没有用于将字符串值转换为对同名变量的引用的内置机制。

您必须手动将变量名称映射到变量。您可以构建一个查找表,将字符串值与相应变量的地址相关联:

struct vn {
  char *varname;
  void *addr;
  Typeinfo t;
};

哪里Typeinfo是一些枚举或其他编码变量类型的机制,给你一些效果

int foo;
double bar;
char *blurga;
struct vn varsByName[] = { {"foo", &foo, IntType}, 
                           {"bar", &bar, DoubleType}, 
                           {"blurga", blurga, CharPtrType} };

我不建议这样做。

于 2013-11-01T14:17:02.350 回答
0

对于少量变量,您的算法应该表现良好。如果有许多变量可以改变,而不仅仅是两个,那么应该考虑另一种算法。在 C 中使这个漂亮和清晰并不是很容易。如果你真的希望它更快,你可以做一个哈希表或使用一个开关/案例,如:

int First, Second; // Note that I got rid of your leading n
char sInput[10];
printf("Which variable to change to 10?");
scanf("%s", &sInput);
// BAD - inflexible and unmaintainable
// referring to character array overflow potential, I assume

switch (sInput[0])
{
     case 'F':
         if (0 == strcmp("irst", sInput+1) )
         {
              First = 10;
         } else 
         {
              // error
         }
         break;
    case 'S':
         if (0 == strcmp("econd", sInput+1) )
         {
              Second = 10;
         } else 
         {
              // error
         }
         break;
    default:
         // error
         break;
}

如果您不喜欢它的外观,那么您可以使用宏 ( #define) 使其看起来不那么大,但结果是一样的。您可以采用的另一种选择是编写一个小程序,输出该程序的源代码,该程序将处理所有重复和乏味的部分。

另一种方法是,如果所有变量都属于同一类型,则创建它们的数组并输入它们的索引而不是名称,但是您必须添加代码以检查是否输入索引数组的大小范围。

于 2013-11-01T14:49:25.683 回答
0

您可以实现诸如字典或包含“变量名称”和值的二维数组之类的东西。然后这归结为将数组元素设置为新值。

除此之外:C# 和其他面向对象的语言将允许通过反射实现这一点,但由于 C 本身不是面向对象的,因此您不能这样做(C++ 对此的支持似乎非常有限)。

于 2013-11-01T12:01:45.103 回答
0

另一种依赖于平台的方法是将所有变量放入共享库中,然后通过名称访问它们。看看 dlsym/dlopen 函数。

void* handle = dlopen("mysymbols.so", RTLD_LOCAL | RTLD_LAZY);
int* var = (int*) dlsym(handle, user_typed_name);
*var = 10; /* modify the variable */
于 2013-11-01T12:11:12.503 回答
0

你可以用宏来做到这一点:

#define MAYBESET(name) if (strcmp(sInput, #name) ==0 ){ name = 10; }

#namename更改为字符串文字的实际值。

于 2013-11-01T12:33:36.373 回答