我正在研究某种脚本语言。包含结构的值是
struct myvar
{
char name[NAMELEN];
int type;
void* value;
}
type = 0 --> int* value
type = 1 --> char* value
type = 2 --> float* value
我遇到了算术运算的一些问题。似乎我需要在每个操作上提交各种类型的转换,这会转换为为每个操作编写一大堆代码,如:
case 0: // "="
if(factor1.name)
{
if((factor1.type == 1) && (factor2.type==1))
{
free(factor1.value);
int len = (strlen((STRING)factor2.value)+1)*sizeof(char);
factor1.value = malloc(len);
memcpy(factor1.value,factor2.value,len);
}
else if((factor1.type == 2) && (factor2.type==2))
*(FLOAT*)factor1.value = *(FLOAT*)factor2.value;
else if((factor1.type == 0) && (factor2.type==0))
*(INTEGER*)factor1.value = *(INTEGER*)factor2.value;
else if((factor1.type == 0) && (factor2.type==2))
*(INTEGER*)factor1.value = *(FLOAT*)factor2.value;
else if((factor1.type == 2) && (factor2.type==0))
*(FLOAT*)factor1.value = *(INTEGER*)factor2.value;
else
GetNextWord("error");
}
break;
有没有办法避免这种令人厌烦的程序?否则我别无选择,只能为“=”,“〜”,“+”,“ - ”,“*”,“/”,“%”,“>”中的每一个复制粘贴这段代码, “<”, “&GT =”, “< =”, “==”, “〜=”, “AND”, “OR”
答案 0 :(得分:3)
使用union
而不是struct
作为值:
struct myvar {
enum {
STRING, INT, FLOAT,
} type;
union {
char strval[NAMELEN];
int intval;
float fltval;
} val;
};
然后用你的脚本语言执行赋值运算符:
factor1 = factor2;
根据您要执行的类型获取正确的值:
switch (operand.type) {
case STRING:
printf("%s", operand.val.strval);
break;
case INT:
printf("%d", operand.val.intval);
break;
case FLOAT:
printf("%f", operand.val.fltval);
break;
}
答案 1 :(得分:2)
我建议如下:在应用操作时,首先应该强制操作数类型。例如,如果你的操作数类型是int和float,你应该将int值强制转换为float值,并继续执行float操作。对于所有操作,强制是相同的(或几乎相同的)。通过这种方法,您可以考虑更少的案例。
答案 2 :(得分:2)
如何编写3个toType
函数:
char* toType0(myvar* from)
{
if (from->type == 0) return (char*)(from->value);
else if (from->type == 1) return itoa((int*)from->value);
else...
}
int toType1(myvar* from)
{
//convert to int...
}
然后在转换例程中,您可以执行以下操作:
switch (factor1.type)
{
case 0:
{ char* other = toType0(&factor2);
//assign or add or whatever....
};
break;
case 1:
{ int other = toType1(&factor2);
//assign or add or whatever....
};
break;
...
}