2549 / 1208 / 358
Регистрация: 30.11.2013
Сообщений: 3,826
1

Оператор присваивания по умолчанию

25.11.2014, 15:36. Показов 2741. Ответов 15
Метки нет (Все метки)

Author24 — интернет-сервис помощи студентам
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
#include <iostream>
using namespace std;
 
class Foo
{
private:
    int var;
        //int var = 17;
public:
    /*Foo& operator=(const Foo& right)
    {
        
        return *this;
    }*/
};
void main()
{
    Foo a;
    Foo b;
    a = b;
}
Добрый день, не могу найти где почитать почему по умолчанию оператор присваивания не копирует "мусор" побитово.
0
Лучшие ответы (1)
Programming
Эксперт
94731 / 64177 / 26122
Регистрация: 12.04.2006
Сообщений: 116,782
25.11.2014, 15:36
Ответы с готовыми решениями:

Для шаблонного класса перегрузить оператор присваивания, copy-конструктор, объекты cin и cout, оператор *
Помогите в следующем: Для класса шаблона следует перегрузить оператор присваивания, конструктор...

Оператор присваивания
Добрый день! Помогите, пожалуйста, разобраться. Я не совсем понимаю работу перегруженного...

оператор присваивания
Подскажите пожалуйста, вот я создал класс, конструктор которого создает 2хмерный массив из 2ойного...

оператор присваивания
Привет всем ! Каким образом вызывается оператор присваивания, например, здесь: a = &quot;I &quot;; если в...

15
Форумчанин
Эксперт CЭксперт С++
8215 / 5045 / 1437
Регистрация: 29.11.2010
Сообщений: 13,453
25.11.2014, 15:45 2
C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
#include <iostream>
using namespace std;
 
class Foo
{
private:
    int var;
        //int var = 17;
public:
    Foo(int x) : var(x) {}
    int getVar() const { return var; }
    /*Foo& operator=(const Foo& right)
    {
 
        return *this;
    }*/
};
int main()
{
    Foo a(1);
    Foo b(2);
    a = b;
    std::cout << a.getVar();
}
не понял, в чём проблема?
Что есть мусор?
0
Эксперт по математике/физикеЭксперт С++
2044 / 1363 / 393
Регистрация: 16.05.2013
Сообщений: 3,498
Записей в блоге: 6
25.11.2014, 15:47 3
С чего вы так решили? Все нормально копируется.
MrGluck, мусор - без инициализации:
C++
1
2
3
4
5
6
7
8
9
10
11
12
#include <iostream>
class Foo {
public:
    int var;
};
int main() {
    Foo a;
    Foo b;
    a = b;
    std::cout << a.var << ' ' << b.var << std::endl;
    return 0;
}
0
2549 / 1208 / 358
Регистрация: 30.11.2013
Сообщений: 3,826
25.11.2014, 15:53  [ТС] 4
Оператор присваивания по умолчанию

VS 2013: ошибка компиляции.

Хочу понять согласно какой строке стандарта. Или это VS защищает меня от "неловких ситуаций в дальнейшем", но почему не Warning, а ошибка компиляции.
0
Форумчанин
Эксперт CЭксперт С++
8215 / 5045 / 1437
Регистрация: 29.11.2010
Сообщений: 13,453
25.11.2014, 15:58 5
Я вначале тоже попробовал без инициализации приравнять, также всё ок.

Я, возможно, кэповскую вещь скажу, но компилятор когда не находит явно объявленного оператор присваиваний делает что-то типа этого:
C++
1
2
3
4
5
6
7
8
9
Foo& Foo::operator=(const Foo &rhs)
{
    if (this != &rhs)
    {
        // для каждого поля класса Foo
        this->поле = rhs->поле
        // или же this->поле.operator=(rhs->поле)
    }
}
Поэтому, когда в классе есть указатели на динамич. память, требуется оператор определить явно т.к. иначе он сделает
указатель lhs = указатель rhs. В итоге, два указателя будут указывать на одну и ту же область памяти и есть риск, что произойдёт ошибка с попыткой повторного освобождения памяти.

Добавлено через 1 минуту
Наверняка, стоит флаг /WX
Свойства проекта > C/C++ > Treat Warnings As Errors.
1
Эксперт по математике/физикеЭксперт С++
2044 / 1363 / 393
Регистрация: 16.05.2013
Сообщений: 3,498
Записей в блоге: 6
25.11.2014, 15:58 6
Лучший ответ Сообщение было отмечено rikimaru2013 как решение

Решение

rikimaru2013, потому, что MS слишком много на себя берет.
1
Форумчанин
Эксперт CЭксперт С++
8215 / 5045 / 1437
Регистрация: 29.11.2010
Сообщений: 13,453
25.11.2014, 15:59 7
Цитата Сообщение от Ilot Посмотреть сообщение
rikimaru2013, потому, что MS слишком много на себя берет.
это обычный варнинг
http://msdn.microsoft.com/ru-r... fhh6x.aspx
0
2549 / 1208 / 358
Регистрация: 30.11.2013
Сообщений: 3,826
25.11.2014, 16:05  [ТС] 8
Цитата Сообщение от MrGluck Посмотреть сообщение
Наверняка, стоит флаг /WX
Свойства проекта > C/C++ > Treat Warnings As Errors.
Проверил c:
Yes (/WX)
No (/WX-)
стоит по умол No (/WX-)

Добавлено через 3 минуты
Всем спасибо за помощь, соглашусь с Ilot, в стандарте ничего не нашёл про это, поэтому это MS решило помоч нам. И никак не отключить ошибку компиляции )))
0
Форумчанин
Эксперт CЭксперт С++
8215 / 5045 / 1437
Регистрация: 29.11.2010
Сообщений: 13,453
25.11.2014, 16:28 9
Цитата Сообщение от rikimaru2013 Посмотреть сообщение
И никак не отключить ошибку компиляции )))
Сейчас посмотрел - да, для свойств классов они генерируют ошибку компиляции. Но можно отключить в Exceptions в Native Run-Time Check(сейчас найду как до этого меню дойти) и возможно ещё кое-где. Напишу инструкцию попозже.

Добавлено через 31 секунду
Но это поведение точно не по стандарту и является инициативой MS. Ilot прав.

Код достаточно обрамить макросами
C++
1
2
#pragma runtime_checks( "", s )
#pragma runtime_checks( "", restore )
Добавлено через 4 минуты
А ещё лучше - правой клавишей по проекту > Properties > C/C++ > Code Generation > Basic Runtime Checks > выбрать Stack Frames (/RTCs)

Добавлено через 1 минуту
http://msdn.microsoft.com/en-u... sb93x.aspx
1
Вездепух
Эксперт CЭксперт С++
11689 / 6368 / 1723
Регистрация: 18.10.2014
Сообщений: 16,051
25.11.2014, 17:39 10
Цитата Сообщение от rikimaru2013 Посмотреть сообщение
не копирует "мусор" побитово.
В С++ копирующий оператор присваивания, определенный компилятором, никогда ничего не копировал "побитово". Концепции "побитового" копирования на уровне ядра языка в С++ просто нет.

Цитата Сообщение от rikimaru2013 Посмотреть сообщение
Или это VS защищает меня от "неловких ситуаций в дальнейшем", но почему не Warning, а ошибка компиляции.
Это warning, а не ошибка компиляции. А erorr он стал потому, что где-то в настройках проекта вы специально попросили, чтобы этот warning стал erorr. Вопрос лишь - где.

Цитата Сообщение от MrGluck Посмотреть сообщение
Код достаточно обрамить макросами
C++
1
2
#pragma runtime_checks( "", s )
#pragma runtime_checks( "", restore )
Эти установки управляют проверками времени выполнения, а в данном случае речь идет об ошибке времени компиляции.

Цитата Сообщение от rikimaru2013 Посмотреть сообщение
Хочу понять согласно какой строке стандарта.
Строка стандарта тут очень простая. Чтение значения неинициализированного объекта приводит к неопределенному поведению.

4.1 Lvalue-to-rvalue conversion [conv.lval]
1 A glvalue (3.10) of a non-function, non-array type T can be converted to a prvalue.53 If T is an incomplete type, a program that necessitates this conversion is ill-formed. If the object to which the glvalue refers is not an object of type T and is not an object of a type derived from T, or if the object is uninitialized, a program that necessitates this conversion has undefined behavior.
Проявления неопредленного поведения не ограничены временем выполнения, а могут выражаться также и в в отказе компилятора компилировать программу.

1.3.24 [defns.undefined] undefined behavior
behavior for which this International Standard imposes no requirements
[ Note: Undefined behavior may be expected when this International Standard omits any explicit definition of behavior or when a program uses an erroneous construct or erroneous data. Permissible undefined behavior ranges from ignoring the situation completely with unpredictable results, to behaving during translation or program execution in a documented manner characteristic of the environment (with or without the issuance of a diagnostic message), to terminating a translation or execution (with the issuance of a diagnostic message). Many erroneous program constructs do not engender undefined behavior; they are required to be diagnosed.
—end note ]
Считайте, что именно это и произошло в вашем случае. Так что формально тут придраться не к чему. А фактически - вопрос в том, как вы умудрились превратить warning C4700 в error. Смотрите в настройки проекта.
1
Форумчанин
Эксперт CЭксперт С++
8215 / 5045 / 1437
Регистрация: 29.11.2010
Сообщений: 13,453
25.11.2014, 17:49 11
Цитата Сообщение от TheCalligrapher Посмотреть сообщение
А фактически - вопрос в том, как вы умудрились превратить warning C4700 в error. Смотрите в настройки проекта.
Цитата Сообщение от MrGluck Посмотреть сообщение
Сейчас посмотрел - да, для свойств классов они генерируют ошибку компиляции.
У них такое идёт независимо от флага Treat Warnings As Errors.

Цитата Сообщение от TheCalligrapher Посмотреть сообщение
Эти установки управляют проверками времени выполнения, а в данном случае речь идет об ошибке времени компиляции.
sdl проверки ещё выключить. Просто даже при их выключении он в рантайме пробует проверить.
0
Вездепух
Эксперт CЭксперт С++
11689 / 6368 / 1723
Регистрация: 18.10.2014
Сообщений: 16,051
25.11.2014, 18:32 12
Цитата Сообщение от MrGluck Посмотреть сообщение
У них такое идёт независимо от флага Treat Warnings As Errors.
Это у кого - "у них"? Я только что попытался скомпилировать этот же код VS 2013 Update 4. Никакого error я не получил. Только warning C4700.

Цитата Сообщение от MrGluck Посмотреть сообщение
sdl проверки ещё выключить.
В моем случае я попробовал включить SDL проверки. Но warning остался warning-ом. Так что что именно у ТС там такое еще включено (если не warnings as errors) я не знаю.

Добавлено через 12 минут
ТС надо показать нам командную строку cl.exe из свойств проекта. Там все должно быть видно.
0
2549 / 1208 / 358
Регистрация: 30.11.2013
Сообщений: 3,826
25.11.2014, 18:48  [ТС] 13
Цитата Сообщение от TheCalligrapher Посмотреть сообщение
ТС надо показать нам командную строку cl.exe из свойств проекта. Там все должно быть видно.
C++
1
/GS /analyze- /W3 /Zc:wchar_t /ZI /Gm /Od /sdl /Fd"Debug\vc120.pdb" /fp:precise /D "WIN32" /D "_DEBUG" /D "_CONSOLE" /D "_LIB" /D "_UNICODE" /D "UNICODE" /errorReport:prompt /WX- /Zc:forScope /RTCs /Gd /Oy- /MDd /Fa"Debug\" /EHsc /nologo /Fo"Debug\" /Fp"Debug\TESTING_ONLY.pch"
0
Вездепух
Эксперт CЭксперт С++
11689 / 6368 / 1723
Регистрация: 18.10.2014
Сообщений: 16,051
25.11.2014, 21:26 14
Цитата Сообщение от rikimaru2013 Посмотреть сообщение
...
Дело в SDL.

Происходит вот что: при включенном SDL этот warning превращается в error, но только в Win32 конфигурациях. В x64 кофигурациях включение SDL такого эффекта не имеет: warning остается warning. Я у себя пробовал именно в x64 конфигурации, поэтому и не заметил такого эффекта от SDL.
1
Эксперт С++
8739 / 4317 / 960
Регистрация: 15.11.2014
Сообщений: 9,760
25.11.2014, 23:16 15
Цитата Сообщение от rikimaru2013 Посмотреть сообщение
Добрый день, не могу найти где почитать почему по умолчанию оператор присваивания не копирует "мусор" побитово.
Дефолтный - почленно.

Грубо говоря, для каждого члена класса вызывается operator=
0
Вездепух
Эксперт CЭксперт С++
11689 / 6368 / 1723
Регистрация: 18.10.2014
Сообщений: 16,051
25.11.2014, 23:37 16
Цитата Сообщение от hoggy Посмотреть сообщение
Дефолтный - почленно.
Вот именно - почленно. Но ни разу не "побитово".
0
25.11.2014, 23:37
IT_Exp
Эксперт
87844 / 49110 / 22898
Регистрация: 17.06.2006
Сообщений: 92,604
25.11.2014, 23:37
Помогаю со студенческими работами здесь

Оператор присваивания.
Всем привет!В универе щас работаем с классами и перегрузками.В частности перегрузкой оператора...

Оператор присваивания
Какая разница между оператором &quot;=&quot; и &quot;==&quot; Почему , например , в цикле нужно писать ...

Оператор присваивания
Здравствуйте! Есть класс, в котором перегружены операции сложения и присваивания: void operator...

Оператор присваивания
Почему в этом случае вызывается оператор присваивания Fraction f4; f4 = f1+f2+f3;...


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
16
Ответ Создать тему
Опции темы

КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin
Copyright ©2000 - 2024, CyberForum.ru