memset(this,0,sizeof(*this)) в конструкторе
От: Аноним  
Дата: 30.09.05 10:17
Оценка:
memset(this,0,sizeof(*this)) в конструкторе

ни чем не опасно?
для класса, где все члены инициализирутся нулями,
было бы удобно и не так утомительно, как перечисление бесчисленных мемберов (с риском чего-то забыть).
Re: memset(this,0,sizeof(*this)) в конструкторе
От: pavel_turbin  
Дата: 30.09.05 10:18
Оценка:
Здравствуйте, Аноним, Вы писали:


А>memset(this,0,sizeof(*this)) в конструкторе


А>ни чем не опасно?

упадет класс с виртуальными методами.
Re: memset(this,0,sizeof(*this)) в конструкторе
От: GregZ СССР  
Дата: 30.09.05 10:20
Оценка:
Здравствуйте, Аноним, Вы писали:


А>memset(this,0,sizeof(*this)) в конструкторе

А>ни чем не опасно?
Если класс полиморфный можешь этим потереть vptr.
Не рекомендую.

А>для класса, где все члены инициализирутся нулями,

А>было бы удобно и не так утомительно, как перечисление бесчисленных мемберов (с риском чего-то забыть).
Может лучше пересмотреть реализацию класса?
Re[2]: memset(this,0,sizeof(*this)) в конструкторе
От: srggal Украина  
Дата: 30.09.05 10:27
Оценка:
Здравствуйте, pavel_turbin, Вы писали:


_>упадет класс с виртуальными методами.


Я бы не был так категоричен:

struct foo
{
    virtual bar()
    {
        std::cout << __FUNCTION__ << std::endl;
    }
};

struct baz
    :    public    foo
{
    baz()
    {
        memset(this,0,sizeof(*this));
    }

    virtual bar()
    {
        std::cout << "baz: "<<__FUNCTION__ << std::endl;
    }
};


int _tmain(int argc, _TCHAR* argv[])
{
    baz        b;

    b.bar();

    return 0;
}
... << RSDN@Home 1.1.4 stable rev. 510>>
Re[3]: memset(this,0,sizeof(*this)) в конструкторе
От: srggal Украина  
Дата: 30.09.05 10:30
Оценка:
Здравствуйте, srggal, Вы писали:

Я бы расширил:

Упадет класс с виртуальными методами при полиморфном вызове

Если вот это добавить, то тогда упадет:

    foo *pFoo = &b;
    pFoo->bar();
... << RSDN@Home 1.1.4 stable rev. 510>>
Re: memset(this,0,sizeof(*this)) в конструкторе
От: Глеб Алексеев  
Дата: 30.09.05 10:31
Оценка: 1 (1) +2
Здравствуйте, <Аноним>, Вы писали:


А>memset(this,0,sizeof(*this)) в конструкторе

А>ни чем не опасно?
Безопасно только для POD-типов.
Причем даже для них этот код может делать не то, что ты от него ожидаешь.
Физическое заполнение нулями не обязано соответствовать логическому значению нуля для различных типов (особенно указателей, float и т.д.)
А>для класса, где все члены инициализирутся нулями,
А>было бы удобно и не так утомительно, как перечисление бесчисленных мемберов (с риском чего-то забыть).
Бесчисленные мемберы — это настораживает.
Кроме того, их можно завернуть в класс:
template <typename T>
struct value_initialized {
    value_initialized() : rep_() {
    }
    template <class U>
    value_initialized(U arg) : rep_(arg) {
    }
    operator T()const {
        return rep_;
    }
private:
    T rep_;
};
... << RSDN@Home 1.1.4 stable SR1 rev. 568>>
Re: memset(this,0,sizeof(*this)) в конструкторе
От: Glоbus Украина  
Дата: 30.09.05 10:32
Оценка:
Здравствуйте, Аноним, Вы писали:


А>memset(this,0,sizeof(*this)) в конструкторе


А>ни чем не опасно?

А>для класса, где все члены инициализирутся нулями,
А>было бы удобно и не так утомительно, как перечисление бесчисленных мемберов (с риском чего-то забыть).

А если у тебя в классе будет член — объект некоего класса, для которого по умолчанию вызывается конструктор без параметров, он делает какие-нить свои хитрые инициализирующие действия, а ты потом забиваешь его память нулями — че тогда делать?
Удачи тебе, браток!
Re[3]: memset(this,0,sizeof(*this)) в конструкторе
От: Глеб Алексеев  
Дата: 30.09.05 10:33
Оценка:
Здравствуйте, srggal, Вы писали:

_>>упадет класс с виртуальными методами.


S>Я бы не был так категоричен:


Я не стал бы делать таких уточнений, т.к. здесь явный UB. Который, как известно, иногда выдает ожидаемые (автором кода) результаты.
... << RSDN@Home 1.1.4 stable SR1 rev. 568>>
Re: memset(this,0,sizeof(*this)) в конструкторе
От: Glоbus Украина  
Дата: 30.09.05 10:35
Оценка:
Здравствуйте, Аноним, Вы писали:


А>memset(this,0,sizeof(*this)) в конструкторе


А>ни чем не опасно?

А>для класса, где все члены инициализирутся нулями,
А>было бы удобно и не так утомительно, как перечисление бесчисленных мемберов (с риском чего-то забыть).

В догонку — кроме того ты еще таким образом похеришь таблицу виртуальных методов.
Удачи тебе, браток!
Re[4]: memset(this,0,sizeof(*this)) в конструкторе
От: srggal Украина  
Дата: 30.09.05 10:42
Оценка:
Здравствуйте, Глеб Алексеев, Вы писали:

ГА>Здравствуйте, srggal, Вы писали:


_>>>упадет класс с виртуальными методами.


S>>Я бы не был так категоричен:


ГА>Я не стал бы делать таких уточнений, т.к. здесь явный UB. Который, как известно, иногда выдает ожидаемые (автором кода) результаты.


В принципе согласен, а если this это POD ?
... << RSDN@Home 1.1.4 stable rev. 510>>
Re[5]: memset(this,0,sizeof(*this)) в конструкторе
От: achp  
Дата: 30.09.05 10:44
Оценка: +1 :)
Здравствуйте, srggal, Вы писали:

S>В принципе согласен, а если this это POD ?


Тогда исходный вопрос не может иметь места.
Re[5]: memset(this,0,sizeof(*this)) в конструкторе
От: Lorenzo_LAMAS  
Дата: 30.09.05 10:44
Оценка: +1
Конструктор, в котором ты делаешь мемсет, автоматически делает тип не-ПОДом
Of course, the code must be complete enough to compile and link.
Re[6]: memset(this,0,sizeof(*this)) в конструкторе
От: srggal Украина  
Дата: 30.09.05 10:49
Оценка:
Здравствуйте, Lorenzo_LAMAS, Вы писали:

L_L>Конструктор, в котором ты делаешь мемсет, автоматически делает тип не-ПОДом

Можно ссылку на стандарт, если не рудно ?
... << RSDN@Home 1.1.4 stable rev. 510>>
Простите за оффтоп, спеллчеккер есть ли какой нить встраивае
От: srggal Украина  
Дата: 30.09.05 10:51
Оценка:
Сабж
... << RSDN@Home 1.1.4 stable rev. 510>>
Re[7]: memset(this,0,sizeof(*this)) в конструкторе
От: Lorenzo_LAMAS  
Дата: 30.09.05 10:52
Оценка: 16 (1)
9/4 + 8.5.1
Of course, the code must be complete enough to compile and link.
Re: memset(this,0,sizeof(*this)) в конструкторе
От: _Winnie Россия C++.freerun
Дата: 30.09.05 11:06
Оценка:
Здравствуйте, Аноним, Вы писали:


А>memset(this,0,sizeof(*this)) в конструкторе


А>ни чем не опасно?

А>для класса, где все члены инициализирутся нулями,
А>было бы удобно и не так утомительно, как перечисление бесчисленных мемберов (с риском чего-то забыть).

Для типов без
1) виртуального наследования,
2) без виртуальных функций,
3) без членов/баз, для которых опасна иницализация нулями после их конструктора
4) без, без членов/баз которые к которым эти правила 1,2,3 применяется рекурсивно,
это будет работать.

Лучше делать так. Обнулять память объекта перед вызовом конструктора, в которой лежит объект.
Для объектов в куче можно написать специальный перегруженный operator new.

enum new_zero_t { new_zero };
void *operator new(size_t size, new_zero_t)
{
return memset(::operator new(size), 0, size);
}

Это неудобно для объектов на стеке, но можно написать свою оболочку, вроде boost::optional.
Правильно работающая программа — просто частный случай Undefined Behavior
Re[8]: memset(this,0,sizeof(*this)) в конструкторе
От: srggal Украина  
Дата: 30.09.05 11:14
Оценка:
Здравствуйте, Lorenzo_LAMAS, Вы писали:

L_L>9/4 + 8.5.1


Спасибо
... << RSDN@Home 1.1.4 stable rev. 510>>
Re[2]: memset(this,0,sizeof(*this)) в конструкторе
От: Erop Россия  
Дата: 30.09.05 11:51
Оценка:
Здравствуйте, _Winnie, Вы писали:


_W>Лучше делать так. Обнулять память объекта перед вызовом конструктора, в которой лежит объект.

_W>Для объектов в куче можно написать специальный перегруженный operator new.

_W>enum new_zero_t { new_zero };

_W>void *operator new(size_t size, new_zero_t)
_W>{
_W> return memset(::operator new(size), 0, size);
_W>}

_W>Это неудобно для объектов на стеке, но можно написать свою оболочку, вроде boost::optional.


А может проще не забыть перечислить все члены класса?
Все эмоциональные формулировки не соотвествуют действительному положению вещей и приведены мной исключительно "ради красного словца". За корректными формулировками и неискажённым изложением идей, следует обращаться к их автором или воспользоваться поиском
Re: memset(this,0,sizeof(*this)) в конструкторе
От: Erop Россия  
Дата: 30.09.05 11:59
Оценка:
Здравствуйте, Аноним, Вы писали:


А>memset(this,0,sizeof(*this)) в конструкторе


А>ни чем не опасно?

А>для класса, где все члены инициализирутся нулями,
А>было бы удобно и не так утомительно, как перечисление бесчисленных мемберов (с риском чего-то забыть).

На самом деле бывает ещё и смежная проблема -- когда надо писать читать все поля в файл.
Но при это мкласс не POD, могут быть какие-то непростые поля, скажем std::string или там функции виртуальные.

Это проблемы примерно одного сорта.
Самое хорошее решение, во всяком случае самое понятное, таки перечислять все поля.
Но если уж такое делать от чего-то совсем никак нельзя, то я пользуюсь таким трюком:


class MyClassPODData {
public:   
    PODType1 field1;
    PODType2 field2;
    //  ...
    PODTypeN fieldN;
};

class MyClass : public MyClassPODData {
//   тут можно определять virtual функции, поля с конструкторами и прочие "неудобные" для хаккерства вещи
};



Ну а чтобы, например, заполнить нулями нашу POD-часть класса, делаем так:

    memset( (public MyClassPODData*)this, 0, sizeof( public MyClassPODData ) );


Ну и с остальными операциями поступаем анологично.
Все эмоциональные формулировки не соотвествуют действительному положению вещей и приведены мной исключительно "ради красного словца". За корректными формулировками и неискажённым изложением идей, следует обращаться к их автором или воспользоваться поиском
Re: memset(this,0,sizeof(*this)) в конструкторе
От: Xander Zerge Россия www.zerge.com
Дата: 30.09.05 12:21
Оценка:
Здравствуйте, Аноним, Вы писали:


А>memset(this,0,sizeof(*this)) в конструкторе


А>ни чем не опасно?

А>для класса, где все члены инициализирутся нулями,
А>было бы удобно и не так утомительно, как перечисление бесчисленных мемберов (с риском чего-то забыть).

А завалить таблицу указателей на виртуальные функции?
Серёжа Новиков,
программист
Подождите ...
Wait...
Пока на собственное сообщение не было ответов, его можно удалить.