Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/cplusplus/159.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C++ 带有一些非公共部分的模板函数_C++_Templates - Fatal编程技术网

C++ 带有一些非公共部分的模板函数

C++ 带有一些非公共部分的模板函数,c++,templates,C++,Templates,我想我应该为这里的OT负责,请原谅我-以防万一- 我有一个小问题,我觉得它比真正的编程问题更哲学,但仍然让我感到不舒服,我希望有一些专家的意见 让我们假设我们正在使用一个模板函数,该函数对所有可能的类型T的行为方式几乎相同,允许对其进行操作: //Perform the rendering template< typename T > long drawing_facility::render( typename object_cnt< T >::type& el

我想我应该为这里的OT负责,请原谅我-以防万一-

我有一个小问题,我觉得它比真正的编程问题更哲学,但仍然让我感到不舒服,我希望有一些专家的意见

让我们假设我们正在使用一个模板函数,该函数对所有可能的类型
T
的行为方式几乎相同,允许对其进行操作:

//Perform the rendering
template< typename T >
long drawing_facility::render( typename object_cnt< T >::type& elements, draw_type type )
{
    ....
    //Any computation needed?
    if( !obj->render_init_done.test_and_set( std::memory_order::memory_order_acquire ) )
    {
        ....
    }
    ....
}
但这是解决问题的更好方法吗?现在,对
render
的a调用意味着另外两个函数调用,这应该不会太多,除非我能够保证
render\u part\u a
render\u part\u b
的独立性,实际上我可以,但只有通过一些肮脏的破解和微妙的参数解决方法

谢谢

小更新:在@Nim的建议之后,我认为这个问题可以通过使用一些重载函数来解决,请看一看这个非常基本的例子,在这个例子中,我从render中删除了第二个参数-不再需要了-:

typedef enum draw_type {
    draw_text = 0,
    draw_vertex = 1
} draw_type;

class drawable
{
public:
    virtual void foo() = 0;
};

class text : drawable
{
public:
    void foo() {};
};

class vertex : drawable
{
public:
    void foo(){};
};

template< typename T >
class drawable_object
{ };

template< typename T >
struct object_cnt
{
    typedef std::vector< std::shared_ptr< drawable_object< T > > > type;
};

class drawing_facility
{
    void special( drawable_object< text >* obj )
    {
         std::cout<<"text\n";
    }
    void special( drawable_object< vertex >* obj )
    {
        std::cout<<"vertex\n";
    }
    public:
        template< typename T >
        long render( typename object_cnt< T >::type& elements )
        {
            //...
            for( auto obj : elements )
            {
                //...
                //the 'if' statement should be here.
                special( obj.get() );
                //...
            }
       //...
       }
};

int main()
{
    typename object_cnt< text >::type a;
    a.push_back( shared_ptr< drawable_object< text > >() );
    typename object_cnt< vertex >::type b;
    b.push_back( shared_ptr< drawable_object< vertex > >() );
    drawing_facility draw;
    draw.render< text >( a );
    draw.render< vertex >( b );
}
typedef枚举绘制类型{
绘制文本=0,
绘制顶点=1
}牵引式;
类可绘制
{
公众:
虚拟void foo()=0;
};
类文本:可绘制
{
公众:
void foo(){};
};
类顶点:可绘制
{
公众:
void foo(){};
};
模板
类可绘制对象
{ };
模板
结构对象
{
typedef std::vector>>类型;
};
类绘图设备
{
void特殊(可绘制对象*obj)
{
std::cout::a型;
a、 向后推(共享的\u ptr>());
typename对象\u cnt::类型b;
b、 向后推(共享\u ptr>());
图纸和设施图纸;
绘制。渲染(a);
绘制。渲染<顶点>(b);
}

希望代码足够清晰。

如果在代码中使用内联模板专门化功能而不是
的话会更好吗?这应该没有性能问题

您采用的第二种策略对我来说没有意义

我确实会使用您最初的方法,但是对于专门的计算,例如,为每个
T
重载一个函数

struct A{}; struct B{}; struct C{};

void compute(A& obj)
{ 
  // code for A
}

void compute(B& obj)
{ 
  // code for B
}

void compute(C& obj)
{ 
  // code for C
}

template <typename T>
void render(T& obj)
{
  .. // common stuff

  if (!obj.computed())
  {
    // now call overloaded function
    compute(obj);
  }

  .. // common stuff
}
结构A{};结构B{};结构C{}; 无效计算(A&obj) { //密码 } 无效计算(B&obj) { //B代码 } 空隙计算(C&obj) { //C代码 } 模板 无效渲染(T&obj) { ..//普通物品 如果(!obj.computed()) { //现在调用重载函数 计算(obj); } ..//普通物品 }
< /代码>我不太确定我理解你的问题。你说的是<代码>如果以及它的代码在某些类型上是如何不同的,但是你的解决方案并没有显示出对该部分的任何改变。也许我删除了太多的代码,在if语句中,代码检查类型的值并执行正确的动作。ting,如果你发现一个有用的答案。这是一个好主意,我制作了一个小的PoC,它工作得很好,我将用一个小的代码示例跟进。
struct A{}; struct B{}; struct C{};

void compute(A& obj)
{ 
  // code for A
}

void compute(B& obj)
{ 
  // code for B
}

void compute(C& obj)
{ 
  // code for C
}

template <typename T>
void render(T& obj)
{
  .. // common stuff

  if (!obj.computed())
  {
    // now call overloaded function
    compute(obj);
  }

  .. // common stuff
}