2012-11-10 26 views
5

Tôi có codeblock sau Tôi đang sử dụng cho khoan động từ Tiếng Đức:Mã động trong C

if (strcmp(*option, "sein") == 0) 
    *option = linie.sein; 

if (strcmp(*option, "haben") == 0) 
    *option = linie.haben; 

if (strcmp(*option, "possessiv") == 0) 
    *option = linie.possessiv; 

if (strcmp(*option, "reflexiv") == 0) 
    *option = linie.reflexiv; 

if (strcmp(*option, "accusativ") == 0) 
    *option = linie.accusativ; 

if (strcmp(*option, "dativ") == 0) 
    *option = linie.dativ; 

Tuy nhiên tôi muốn ngưng tụ nó để cái gì đó như:

*option = linie.(*option); 

Hoặc có lẽ:

*option = linie.(*option)(); 

Thật không may, cả hai đều không hoạt động. Bất kỳ ý tưởng?

Sửa @dasblinkenlight:

typedef struct 
{ 
    char subjekt[20]; 
    char sein[20]; 
    char haben[20]; 
    char possessiv[20]; 
    char reflexiv[20]; 
    char accusativ[20]; 
    char dativ[20]; 
} satz; 

satz linie = 
{ 
    .subjekt = "", 
    .sein = "", 
    .haben = "", 
    .possessiv = "", 
    .reflexiv = "", 
    .accusativ = "", 
    .dativ = "" 
}; 

char *option = argv[1]; 
+0

Xin chỉ cho định nghĩa của 'linie' và 'option'. – dasblinkenlight

+0

Vùng chứa và vòng lặp. Bạn thực sự nên học "Quy tắc 0-1-Nhiều". –

+3

Thật không may điều này là không thể trong C, vì nó không có khả năng phản xạ hoặc mã động. –

Trả lời

4

Bạn đang trộn thời gian biên dịch và các tùy chọn thời gian chạy. Trong C, bạn không thể sử dụng một định danh trực tiếp từ một chuỗi có thời gian chạy. Tuy nhiên, bạn có thể mang comparaisons của bạn thành một hàm mờ đục.

char *f(const satz *linie, const char *option) 
{ 
    if (strcmp(option, "sein") == 0) 
     return linie->sein; 
    else if (strcmp(option, "haben") == 0) 
     return linie->haben; 
    else if (strcmp(option, "possessiv") == 0) 
     return linie->possessiv; 
    else if (strcmp(option, "reflexiv") == 0) 
      return linie->reflexiv; 
    else if (strcmp(option, "accusativ") == 0) 
     return linie->accusativ; 
    else if (strcmp(option, "dativ") == 0) 
     return linie->dativ; 
    else 
     return NULL; 
} 

*option = f(&linie, *option); 
+0

Bạn nói đúng về việc trộn các chuỗi thời gian và các chuỗi thời gian chạy Kirilenko. Tôi sẽ nói điều này là tốt như nó sẽ nhận được. Cảm ơn bạn vì câu trả lời. – user1408643

5

Câu trả lời của Kirilenko là câu trả lời hay và hoạt động tốt cho các cấu trúc ngắn như của bạn. Tuy nhiên, đối với các cấu trúc dài hơn, việc duy trì tất cả các cuộc gọi strcmp có thể rất cồng kềnh. Để giải quyết điều này, bạn có thể xác định mối quan hệ giữa từ khóa bạn đang cố gắng so khớp và phần bù của phần tử tương ứng trong cấu trúc của bạn.

struct relation 
{ 
    char keyword[20]; 
    int offset; 
}; 

Sau đó, bạn có thể sử dụng macro offset (trong stddef.h) để liên kết từ khóa với vị trí của nó trong cấu trúc của bạn.

#define REL_LEN (7) 

struct relation rel[REL_LEN] = { 
    {"subjekt", offsetof(satz, subjekt) }, 
    {"sein", offsetof(satz, sein) }, 
    {"haben", offsetof(satz, haben) }, 
    {"possessiv", offsetof(satz, possessiv) }, 
    {"reflexiv", offsetof(satz, reflexiv) }, 
    {"accusativ", offsetof(satz, accusativ) }, 
    {"dativ", offsetof(satz, dativ) } 
}; 

Cuối cùng, chức năng truy xuất chuỗi ký tự của bạn bằng cách sử dụng ánh xạ ở trên có thể trông giống như thế này.

char *lookup_keyword(const satz *linie, const char *option, 
        const struct relation *rel, size_t rel_size) 
{ 
    int i; 
    char *pchar = (char *)linie; 

    for (i=0; i<rel_size; i++) 
    { 
     if (strcmp(option, rel->keyword) == 0) 
     { 
      pchar += rel->offset; 
      return pchar; 
     } 
     rel++; 
    } 
    printf("Error: no mapping found matching %s!\n", option); 
    return ""; 
} 

Và bạn có thể gọi nó như vậy

char *option = argv[1]; 

printf("Result for %s: %s\n", option, 
     lookup_keyword(&linie, option, rel, REL_LEN));