2012-01-07 2 views
2

Я знаю, что функция может проходить через аргумент template, могу ли я передать класс Constructor следующим образом.Пропустить класс Конструктор через аргумент шаблона в C++

Update: Вся причина, по которой я хочу, чтобы это сделать, это я могу выбрать конструктор в пуле памяти и без какого-либо кода, изменяющегося в классе я хочу Alloc (в данном случае class A)

class A 
{ 
public: 
    A(){n=0;} 
    explicit A(int i){n=i;} 

private: 
    int n; 
}; 

class MemoryPool 
{ 
public: 
    void* normalMalloc(size_t size); 
    template<class T,class Constructor> 
    T* classMalloc(); 
}; 

template<class T,class Constructor> 
T* MemoryPool::classMalloc() 
{ 
    T* p = (T*)normalMalloc(sizeof(T)); 
    new (p) Constructor; // choose constructor 
    return p; 
} 

MemoryPool pool; 
pool.classMalloc<A,A()>(); //get default class 
pool.classMalloc<A,A(1)>(); 
+0

'A()' в шаблоне аргумента обозначает тип функции, не принимая никаких аргументов и возвращает 'Ā'. – Xeo

+1

Не могли бы вы предоставить еще несколько контекстов? Учитывая только эту небольшую информацию, я бы спросил себя: почему бы не использовать 'new A()' непосредственно вместо 'new_func '? Иными словами, что вы покупаете 'new_func'? Снимает ли он абстрактное строительство? – Andre

+0

@Andre Причина в том, что я хочу использовать его в пуле памяти, чтобы я мог malloc класс с выбором конструкции – xucheng

ответ

5

вы не можете обойти конструкторы, но вы можете пройти вокруг фабричных функторов:

class A 
{ 
    int n; 

    A(int i) : n(i) {}; 

public: 

    static A* makeA(int i) 
    { 
     return new A(i); 
    } 
}; 

template<typename T, typename Factory> 
T* new_func(Factory factory) 
{ 
    return factory(); 
} 

#include <functional> 

int main() 
{ 
    new_func<A>(std::bind(&A::makeA, 0)); 
    new_func<A>(std::bind(&A::makeA, 1)); 
} 
+0

Вся причина, по которой я хочу это сделать, заключается в том, что я могу выбрать конструктор в пуле памяти и без изменения кода в классе, который я хочу выделить – xucheng

4

Все ваше предположение неверно. Вам не нужна эта функция.

template<class T> 
T* new_func() 
{ 
    return new T; 
} 

Вещи после new типа, а не ссылка конструктора.

+0

. О различии между 'new A()' и 'new A (1) ' – xucheng

+1

Это не« передает конструктор ». Это приведет к полному списку аргументов. Это даже не работает для обычных аргументов шаблона указателя функции (члена). Конечно, вы должны передать это как обычные аргументы функции, а не как аргументы шаблона. Прочитайте или спросите о «идеальной пересылке». –

+1

Добавьте параметр в 'new_func()': 'T * new_func (int i = 0)' и передайте его конструктору. – hmjd

0

Таким образом, лучше я думаю

template<class T, int n> 
struct Factory 
{ 
    static T* new_func() 
    { 
    return new T(n); 
    } 
}; 

template<class T> 
struct Factory<T,0> 
{ 
    static T* new_func() 
    { 
    return new T; 
    } 
}; 

T* t = Factory<T>::new_func(); //call default constructor 
T* t2 = Factory<T,2>::new_func(); //call constructor T(2) 
+0

. Вся причина, по которой я хочу это сделать, - это выбор конструктора в пуле памяти и без изменения кода в классе, который я хочу выделить – xucheng

+0

Вы можете использовать стиль Factory в вашем классе пула памяти. – nttstar

+0

Досадно, что каждый раз, когда я его использую. Мне нужно написать новую структуру Factory, так как аргумент конструктора класса malloc неизвестен – xucheng

Смежные вопросы