2

这是关于C编程语言的。

我有大量的二维数组(sizes are not fixed)。考虑以下示例。

bool sym_a[][]={{...},{...},...};  //consider these are initialized properly
bool sym_b[][]={{...},{...},...};
...
bool sym_z[][]={{...},{...},...};
bool sym_0[][]={{...},{...},...};
bool sym_1[][]={{...},{...},...};
...
bool sym_9[][]={{...},{...},...};
...

注意命名约定,所有的名字都是一样的。只有数组名称的最后一个字符会改变(如果它可以超过一个字符会更好,但这并不重要)。

好的,现在我有一个功能。它根据传递的参数选择其中一个二维数组。然后对选定的数组执行一些任务。请注意,任务是一个常见的任务,只有选定的数组被更改。

例如,根据我目前能想到的,是的switch-case,我可以实现如下功能。

void doStuff(char letter){
    switch(letter){
        case 'a':
            sym_a[0][0]=1;  //just for demonstration :D
        break;
        case 'b':
            sym_b[0][0]=1;  //same thing, only the character 'a' changed to 'b'
        break;
        ...
        case 'z':
            sym_z[0][0]=1;
        break;
        case '0':
            sym_0[0][0]=1;
        break;
        case '1':
            sym_1[0][0]=1;
        break;
        ...
        ...
    }    
}

但必须有更好的方法。如果我有 1000 个这样的数组,那么我是否必须编写 1000 个这样的案例?对于所有情况,内容完全相同。只有变量名的一个字符被更改。

如果有类似字符串连接的东西会很好。

#define conc(a,b) a ## b

然后conc(sym_,a)将代表sym_a。但这不能直接应用在这里。因为我不能将确切的字母传递给 的右侧参数conc(a,b),所以只能传递包含所需字母的变量。

void doStuff(char letter){
    conc(sym_,letter)[0][0]=1;
}

conc(sym_,letter)sym_letter. 但我需要sym_与字符变量的内容连接letter

例如,如果我打电话给doStuff('b');他们sym_b,应该给出,而不是sym_letter.

希望我的要求清楚。这件事看起来很简单,但我想不出办法摆脱它。请注意,二维数组的大小(行数/列数)不是固定的。否则我可以使用 3D 数组。

任何想法都值得赞赏。

4

3 回答 3

2

你有大量的静态数组,所以它可能是一个自然的扩展,你最终会有大量的条件来访问它们。

您可以定义一个额外的静态数组,将字符代码映射到一个数组。

static const struct {
  char* lookup_code;
  bool **array;
} char_code_lookup[] = {
    { .lookup_code = "a", sym_a },
    { .lookup_code = "b", sym_b },
    /* ... */
    { .lookup_code = NULL, NULL }, /* Terminator */
};

然后,您的doStuff函数可以扫描数组以查找适当的查找代码以匹配静态定义的数组。

使用一点宏魔法,您可以同时生成静态数组和静态查找数组以减少重复,但上面列出的方法可能更易于阅读。

或者,您可以使用 动态分配数组malloc,同时在运行时创建数组时关联查找代码。

于 2013-03-28T05:08:19.963 回答
1

Does something like this help? [ Apologies if there's some C++ here. ]

bool** sym_a;
bool** sym_b ;
bool** sym_z;
bool** sym_0;
bool** sym_1;
bool** sym_9 ;


unsigned lowestEntry = 'a';
unsigned highestEntry = '9';
const unsigned numEntries = highestEntry - lowestEntry;

size_t size = sizeof(bool**)* numEntries;

bool*** lookup = (bool***)malloc(size); 

#define conc(a,b) a ## b
#define index(a) #a[0]-'a'
#define add(a) lookup[index(a)] = conc(sym_,a)

void init()
{
    memset(lookup, 0, size);
     add(a);
     add(b);
     add(z);
     add(9);
     add(k); // does not compile, sym_k not defined.
}

bool** findSymbolTable(char val)
{
    return lookup[val - lowestEntry];
}
于 2013-03-28T05:31:01.563 回答
1

分配一个大的 int 数组并将其分区为您的其他变量。

例如。

整数数据[2600];

sym_a 将有前 100 个整数,sym_b 将有前 100 个整数,依此类推。您将能够在这些数组中存储 8 * 100* 4 个布尔值。

现在访问 sym_p[x][y] 你会说你总共有 R 行和 C 列:

int * 开始 = 数据 + (ASCIValue(p) - ASCIValue(a)) * 100;

您必须从头开始读/写位号(C * x + y)。

于 2013-03-28T05:48:16.197 回答