Справочник функций

Ваш аккаунт

Войти через: 
Забыли пароль?
Регистрация
Информацию о новых материалах можно получать и без регистрации:

Почтовая рассылка

Подписчиков: -1
Последний выпуск: 19.06.2015

Создать экземпляр текущего класса

17K
11 января 2007 года
Mexes
10 / / 19.08.2006
Как создать объект такого же класса, как и текущий?

Например:
 
Код:
class A
{
virtual public A MethodFoo() {...}
}


Пусть MethodFoo возвращает объект класса A. Необходимо, чтобы его наследник class B : A при вызове B.MethodFoo() возвращал не A, а B. Без перекрытия метода в B. Т. е. на лету взять текущий класс и создать объект этого типа.
1.8K
11 января 2007 года
_const_
229 / / 26.11.2003
Код:
class A
{
public:
    virtual A *CreateInstance(void) { return new A; };
};

class B : public A
{
public:
    virtual A *CreateInstance(void) { return new B; };
};
17K
11 января 2007 года
Mexes
10 / / 19.08.2006
Вопрос не понят. Нужно как раз избавиться от перекрытия MethodFoo() в наследниках
1.8K
11 января 2007 года
_const_
229 / / 26.11.2003
Действительно, не понят. То есть в наследнике должны быть методы создания и A, и B?
17K
11 января 2007 года
Mexes
10 / / 19.08.2006
Наследник должен возвращать тем же методом созданный объект того же класса (наследника).
Например, мы всегда можем получить актуальный тип объекта GetType(), а как создать экземпляр именно этого класса?
Что-то вроде такого (естественно, не работает):
 
Код:
virtual public A MethodFoo()
{
    Type t=this.GetType();
    return new t();
}
1.8K
11 января 2007 года
_const_
229 / / 26.11.2003
Именно это и сделано в примере. Я не понял, что значит "Нужно как раз избавиться от перекрытия MethodFoo() в наследниках".
18K
11 января 2007 года
Mind Maker
25 / / 11.12.2006
Нужно в базовом классе написать метод возвращающий объект класса наследника, который вызывает этот метод.
Я правильно понял?
11K
11 января 2007 года
.nornad
125 / / 04.01.2007
Не совсем понятно, зачем такое может потребоваться, чтобы ещё и переопределять нельзя было свой метод, но можно попробовать в своём методе использовать клонирование объекта с помощью MemberwiseClone (защищённый метод Object). Я, правда, не пробовал так делать и не гарантирую, что получится. :)
3
11 января 2007 года
Green
4.8K / / 20.01.2000
Создать объект типа не имея никакой информации об этом типе невозможно,
Можно создать метод само-клонирования типа (см. пример _const_).
Можно различными способами получать информацию о типе.
Вариант первый:
Код:
template<class T>
class A
{
public:
    T* CreateInstance(void) {
        return new T;
    }
};

// использование
class B : public A<B>
{
};

Вариант второй:
Код:
class A
{
public:
    template<class T>
    T* clone(T*) {
        return new T;
    }
};

// использование
class B : public A
{
    void func() {
        B* b = clone(this);
    }
};

// использование
B b;
B* pB = b.clone(&b);

В этом случае необязательно, чтобы clone был методом класса, это может быть и просто функция:
Код:
template<class T>
T* clone(T*) {
    return new T;
}

// использование
B b;
B* pB = clone(&b);

string str;
string* pStr = clone(&str);
355
12 января 2007 года
&lt;SCORP&gt;
786 / / 21.10.2006
Код:
class A : public CObject
{
    DECLARE_DYNCREATE(A)
public:
    A() {}
    virtual ~A() {}
    virtual PrintSelf() { printf("I am of class A\n"); }
    A* CreateInstance()
    {
        CRuntimeClass *c = this->GetRuntimeClass();
        return (A*)c->CreateObject();
    }
};

class B : public A
{
    DECLARE_DYNCREATE(B)
public:
    B() {}
    virtual ~B() {}
    virtual PrintSelf() { printf("I am of class B\n"); }
};

IMPLEMENT_DYNCREATE(A, CObject)
IMPLEMENT_DYNCREATE(B, A)

 
Код:
B* b = new B();
b->PrintSelf();
A* a = b->CreateInstance();
a->PrintSelf();

чтобы всё это работало необходимо включить RTTI в свойствах проекта.
сорри за не совсем красивый код -- специально заихнул классы полностью в один файл
Реклама на сайте | Обмен ссылками | Ссылки | Экспорт (RSS) | Контакты
Добавить статью | Добавить исходник | Добавить хостинг-провайдера | Добавить сайт в каталог