C++ C++;使用具有许多实例的模板方法初始化,这些实例在编译时消耗大量内存

C++ C++;使用具有许多实例的模板方法初始化,这些实例在编译时消耗大量内存,c++,qt,templates,qxorm,C++,Qt,Templates,Qxorm,我有一个带有模板方法的类,我实例化了许多其他类,比如100多个。问题是模板类的编译会消耗大量内存,比如3GB。我假设发生这种情况是因为有许多模板实例。为了详细说明,实例化的类是Qt和QxOrm对象。 其他人也没有这个问题吗? 有人建议如何减少内存消耗 以下是代码的一些部分: //The class with template methods class SGSRequestHandler : public HttpRequestHandler { public: SGS

我有一个带有模板方法的类,我实例化了许多其他类,比如100多个。问题是模板类的编译会消耗大量内存,比如3GB。我假设发生这种情况是因为有许多模板实例。为了详细说明,实例化的类是Qt和QxOrm对象。 其他人也没有这个问题吗? 有人建议如何减少内存消耗

以下是代码的一些部分:

//The class with template methods

class SGSRequestHandler : public HttpRequestHandler
{
    public:
        SGSRequestHandler(QObject* parent = 0);
        virtual ~SGSRequestHandler();

        template<class T>
        ResponseInfo processDatabase(ODataRequestInfo<T>& odata, qx::QxSession& session) {...}

        template<class T>
        ResponseInfo httpGet(ODataRequestInfo<T> &odata, qx::QxSession& session) {...}
    ...
   }


//Here is a example of what I do with de template class:

else if (className == "class1")
     rInfo = process<Class1>(request, session);
else if (className == "class2")
     rInfo = process<Class2>(request, session);
...
else if (className == "class100")
    rInfo = process<Class100>(request, session);
//具有模板方法的类
类SGSRequestHandler:公共HttpRequestHandler
{
公众:
SGSRequestHandler(QObject*parent=0);
虚拟~SGSRequestHandler();
模板
ResponseInfo进程数据库(ODataRequestInfo&odata,qx::QxSession&session){…}
模板
ResponseInfo-httpGet(ODataRequestInfo&odata,qx::QxSession&session){…}
...
}
//下面是我对de模板类所做操作的示例:
else if(className==“class1”)
rInfo=进程(请求、会话);
else if(className==“class2”)
rInfo=进程(请求、会话);
...
else if(className==“class100”)
rInfo=进程(请求、会话);

最简单的解决方案可能是使用100个实例化并将其移动到多个.cpp文件中

我想到了一个解决办法。甚至离优雅不近,但解决了我的问题

我只是将实例化所有模板的类拆分为其他三个类。因此,编译时的内存消耗是每个类的第三部分

请记住,我需要使用模板,因为我使用的是QxOrm库,否则我可以使用polimorfism以更简单的方式完成这项工作

//processorr.h

class ProcessorR {
    void process(const QString& className) {
        if(className == "rClass1")
            rInfo = process<rClass1>(request, session);
        else if(className == "rClass2")
            rInfo = process<rClass2>(request, session);
        /// And so on
    }
}

//processort.h

class ProcessorT {

    void process(const QString& className) {
        if(className == "tClass1")
           rInfo = process<tClass1>(request, session);
        else if(className == "tClass2")
           rInfo = process<tClass1>(request, session);
        /// And so on
    }
}

//And then in usage:

if(className.startsWith("t"))
{
    ProcessorT processor;
    processor.process(className);
}
else if(className.startsWith("r"))
{
    ProcessorR processor;
    processor.process(className);
}
else if(className.startsWith("u"))
{
    ProcessorU processor;
    processor.process(className);
}
//processor.h
类处理器{
无效进程(常量QString和类名称){
如果(类名==“rClass1”)
rInfo=进程(请求、会话);
else if(className==“rClass2”)
rInfo=进程(请求、会话);
///等等
}
}
//processport.h
类处理端口{
无效进程(常量QString和类名称){
如果(类名==“tClass1”)
rInfo=进程(请求、会话);
else if(className==“tClass2”)
rInfo=进程(请求、会话);
///等等
}
}
//然后在使用中:
if(className.startsWith(“t”))
{
处理器端口处理器;
进程(类名称);
}
else if(className.startsWith(“r”))
{
处理器或处理器;
进程(类名称);
}
else if(className.startsWith(“u”))
{
处理器;
进程(类名称);
}

查看您的解决方案表明,模板确实是解决问题的错误答案

<>也许你应该考虑把所有的处理类实例登记到<代码> SGSHandler < /C>类,这样就可以做< /P>
processors_[name].process(request, session);

这显然需要运行时成本,但是在注释后维护类要容易得多。

//模板类不是类模板。好的,它是一个带有模板方法的类,就像我上面写的那样。我正在编辑注释。您需要消耗大量内存,因为编译器必须生成许多不同版本的函数。如果编译过程中的内存是一个约束条件,请研究类型擦除技术以减少模板实例化的数量。
或并行编译类
听起来会成倍增加内存使用;这与高内存消耗的解决方案相反。注释后的类<代码>//带有模板方法的类<代码>未使用。无论如何,使用
if
语句在模板实例之间切换通常表明存在设计问题。这是一个我不知道的聪明的解决方案。但不幸的是,在我的例子中,我只在同一个文件中的每个类上实例化函数。