【问题标题】:how to know the element type of void* array in c++如何知道 C++ 中 void* 数组的元素类型
【发布时间】:2015-01-03 06:23:01
【问题描述】:

首先我在做编译器项目,我已经建立了一个符号表

class SymbolTable
{
    Scope * currScope;
    Scope * rootScope;
...
}

//where scope is 
class Scope{
    Scope();
    Scope * parent;
    MyMap * m;
...
};

//and Mymap is 
class MyMap
{
    static const int mapLength = MAX_LENGTH;
    MapElem * arr[mapLength];
    int hash(char* name);
...
}

//MapElem is

    class MapElem{
        char* name;
        void* elem;
        MapElem * next;
    ...
    }

现在 Void* elem 可以是 ((function , class, variable ,scope)) 所有的 r 类, 我想打印符号表来检查 Yacc 和解析器在做什么! 我试着这样做:

void printScope(Scope *s)
{
    if (s != NULL)
    {
        cout << "{";
        for (int i = 0; i < 71; i++)
        {
            MapElem* tempelem = s->m->getbyId(i);
            while (tempelem != NULL)
            {
                //cout << "element name is" << tempelem->getName();

                if (static_cast <Type*> (tempelem->getElem())){
                    Type* t = (Type*)tempelem->getElem();
                    cout << "element is Class it's name is" << t->getIs_final() << " " << t->get_name() << "(";
                    for (int i = 0; i < t->getInheritedType().size(); i++){
                        if (t->getInheritedType()[i] != NULL)
                        cout << t->getInheritedType()[i]->get_name() << "," << endl;
                    }
                    cout << "):" << endl;
                    printScope(t->getScope());
                }

                else if (static_cast <Function*>(tempelem->getElem())){
                    Function* t = (Function*)tempelem->getElem();
                    cout << "element is Function it's name is" << t->get_final() << " " << t->get_name() << "(";
                    vector<Variable *> paramet = t->getparameters();
                    for (int i = 0;i< paramet.size(); i++){
                        cout << paramet[i]->get_name() << "," << endl;
                    }
                    cout << "):" << endl;
                    printScope(t->getScope());
                }
                else if ((Scope*)tempelem->getElem()){
                    Scope* t = (Scope*)tempelem->getElem();
                    printScope(t);
                }
                else if ((Variable*)tempelem->getElem()){
                    Variable* t = (Variable*)tempelem->getElem();
                    cout << "element is Variable it's name is" << t->getAccessModifier() << " " << t->get_name() << endl;
                }
                tempelem = tempelem->getNext();
            }
        }
        cout << "}"<<endl;
    }


}

代码运行完美,但没有检查 If 语句中的 [void type],即使转换错误,也始终输入第一个条件, 以该顺序始终输入类型,即使 void 是函数或变量 ??? 当我更换它们时,也输入第一个 stmt 它是什么! 为什么 ??以及我该如何解决?或者我怎么知道我必须转换什么数据类型。

【问题讨论】:

  • 一开始就不要扔掉类型信息。
  • 这是 RTTI 或虚函数的工作。
  • static_cast 在运行时不执行任何检查。
  • 您应该使用 C++ 容器,例如std::map
  • @user3312095 - 简单地说,没有魔法可以从空指针获取类型信息。看来您误解了static_cast 所做的事情,并根据这些错误信息编写了一系列代码。

标签: c++ casting void-pointers


【解决方案1】:

传统的答案是给MapElem添加一个枚举来表示类型:

class MapElem{
    //Enumeration identifying all the types of map element and indicating the contents of elem.
    typedef enum {
        aFunction,
        aClass,
        aVariable,
        aScope
    } Type;

    char* name;
    Type type; //<---- Tells us what elem really is!
    void* elem;
    MapElem * next;
...
};

更多的OO方式是为每种类型引入一个基类和子类。 您可能会发现这有点麻烦,因为变量类型(函数、类、变量和范围)是如此不同,以至于您的基类将只包含一种提取类型的方法! 哦,还有一些返回可打印字符串以检查元素的方法......

您可能会引入一个返回枚举类型的虚拟成员或依赖 RTTI。 RTTI 通常是一个错误,表明您不了解多态性,或者它对这种情况没有真正的帮助。 在这种情况下,我怀疑是后者。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2017-04-01
    • 1970-01-01
    • 2018-12-07
    • 1970-01-01
    • 1970-01-01
    • 2019-02-06
    • 2016-03-13
    相关资源
    最近更新 更多