Форум программистов, компьютерный форум, киберфорум
С++ для начинающих
Войти
Регистрация
Восстановить пароль
Блоги Сообщество Поиск  
 
 
Рейтинг 4.95/103: Рейтинг темы: голосов - 103, средняя оценка - 4.95
1 / 1 / 0
Регистрация: 02.08.2012
Сообщений: 15

Отличие объявления, определения и инициализации

26.06.2013, 23:57. Показов 22366. Ответов 42
Метки нет (Все метки)

Студворк — интернет-сервис помощи студентам
Здравствуйте, товарищи.

Читаю тут книжицу по C++, учусь потихоньку.
И возник у меня вопрос нерядового характера: в чём фундаментальное отличие объявления, определения и инициализации? В книге всё намешано, ничего не понятненько.

Однако усёк, что они говаривают, будто такая строка:
C++
1
int a = 3;
не просто присваивание переменной значения, а что-то большее.
И как-то это связано с созданием экземпляров классов.

А ещё пишут, что есть инициализация прямая и инициализация копии.
А потом вот это кажут:
C++
1
2
int val = 1024;
int val (1024);
И говаривают, будто val в обоих случаях будет одинаковой.

Что-то я видно не секу истинной сути.
Помогите словцом мудрым.
0
Лучшие ответы (1)
cpp_developer
Эксперт
20123 / 5690 / 1417
Регистрация: 09.04.2010
Сообщений: 22,546
Блог
26.06.2013, 23:57
Ответы с готовыми решениями:

Правила объявления инициализации
Напишите основные - самые главные правила обьявления инициализации.

В чём отличие разных способов объявления переменных?
в чем отличие int a(2); от int a=2; И как писать правильней

Сложные определения и объявления
Решил создать отдельный топик т.к. ну совсем никак не могу разобраться (все взято с книги) есть вот такая штука void * ...

42
5500 / 4895 / 831
Регистрация: 04.06.2011
Сообщений: 13,587
27.06.2013, 13:14
Студворк — интернет-сервис помощи студентам
Цитата Сообщение от Croessmah Посмотреть сообщение
задание начального правильного значения, а это и есть инициализация
Тогда дейстие в коде (15 пост) можно назвать инициализацией (с применением механизма присваивания)?
Цитата Сообщение от Croessmah Посмотреть сообщение
но только различие в том, какой механизм используется - механизм инициализации или механизм присвоения
Отличие в том, что в механизме инициализации используются конструкторы?
0
Неэпический
 Аватар для Croessmah
18150 / 10732 / 2067
Регистрация: 27.09.2012
Сообщений: 27,047
Записей в блоге: 1
27.06.2013, 13:50
@alsav22, Ну на счет механизмов это я просто так выразился, корректнее, наверное, сказать по другому:
C++
1
int a(1024);//инициализация
C++
1
2
int a;//создаем со значением по умолчанию (в данном случае с мусором)
a=1024;//не инициализация, а присвоение начального значения.
имхо, так будет правильнее
второй случай - инициализация с точки зрения определения инициализации и присвоение с точки зрения языка.
С классами же все совершенно очевидно, ибо при создании будет вызван конструктор, который и должен инициализировать объект, а при присвоении будет вызван оператор присвоения.
0
Почетный модератор
Эксперт С++
 Аватар для SatanaXIII
5851 / 2862 / 392
Регистрация: 01.11.2011
Сообщений: 6,906
27.06.2013, 14:05
Я прошу прощения если не в тему, но нельзя ли перефразировать так:
C++
1
int a;//инициализация мусором
?

0
Неэпический
 Аватар для Croessmah
18150 / 10732 / 2067
Регистрация: 27.09.2012
Сообщений: 27,047
Записей в блоге: 1
27.06.2013, 14:10
@SatanaXIII, Как, правило, нельзя, ибо нет никакой инициализации - просто выделение места с тем значением, которое будет в памяти валяться то есть создание без задания какого-либо значения, имхо.
0
Почетный модератор
Эксперт С++
 Аватар для SatanaXIII
5851 / 2862 / 392
Регистрация: 01.11.2011
Сообщений: 6,906
27.06.2013, 14:26
Цитата Сообщение от Croessmah Посмотреть сообщение
то есть создание без задания какого-либо значения, имхо.
то есть создание без задания какого-либо конкретного значения
0
Ушел с форума
Эксперт С++
 Аватар для Убежденный
16481 / 7444 / 1187
Регистрация: 02.05.2013
Сообщений: 11,616
Записей в блоге: 1
27.06.2013, 14:45
Цитата Сообщение от SatanaXIII Посмотреть сообщение
int a;//инициализация мусором
Это не всегда верно.
Для объектов со статическим временем жизни (static storage duration)
выполняется так называемая инициализация нулем (zero-initialization).
C++
1
2
3
4
5
6
7
8
int a; // Будет равно нулю.
 
int main()
{
    int b; // А вот здесь будет мусор.
 
    return 0;
}
0
5500 / 4895 / 831
Регистрация: 04.06.2011
Сообщений: 13,587
27.06.2013, 14:51
Цитата Сообщение от Croessmah Посмотреть сообщение
С классами же все совершенно очевидно, ибо при создании будет вызван конструктор, который и должен инициализировать объект
Предположим, был вызван конструктор по умолчанию, который ничего не сделал и в полях объекта остался мусор. Объект всё равно считается инициализированным? Или нет? Почему тогда:
C++
1
int a; // неинициализированный объект
Ведь то же самое (может даже и конструктор по умолчанию вызывается).
0
Неэпический
 Аватар для Croessmah
18150 / 10732 / 2067
Регистрация: 27.09.2012
Сообщений: 27,047
Записей в блоге: 1
27.06.2013, 14:57
@alsav22, Конструктор предназначен для инициализации объекта. Он вызван, значит объект можно назвать инициализированным, а то, что программист делает в конструкторе всем наплевать главное, чтобы порносайты при этом не открывались
0
:)
Эксперт С++
4773 / 3267 / 497
Регистрация: 19.02.2013
Сообщений: 9,046
27.06.2013, 14:58
Цитата Сообщение от Убежденный Посмотреть сообщение
int b; // А вот здесь будет мусор.
В общем случае, да. Но на старинном ваткоме в отладочном режиме инициализировалось нулями, насколько я помню. Да и https://ideone.com/uGgHt1 дает 0. Короче говоря, "мусорное" значение вполне детерминированно может быть нулём. Но безусловно это всё не регламентируется стандартом.
0
Ушел с форума
Эксперт С++
 Аватар для Убежденный
16481 / 7444 / 1187
Регистрация: 02.05.2013
Сообщений: 11,616
Записей в блоге: 1
27.06.2013, 15:26
Цитата Сообщение от Tulosba Посмотреть сообщение
Но безусловно это всё не регламентируется стандартом.
Если быть совсем дотошным, то вот:
C++ 2003

8.5 Initializers

...

6. Every object of static storage duration shall be zero-initialized at program
startup before any other initialization takes place.

...

9. If no initializer is specified for an object, and the object is of (possibly cv-qualified)
non-POD class type (or array thereof), the object shall be default-initialized; if the
object is of const-qualified type, the underlying class type shall have a user-declared
default constructor. Otherwise, if no initializer is specified for a non-static
object, the object and its subobjects, if any, have an indeterminate initial value
.
0
Неэпический
 Аватар для Croessmah
18150 / 10732 / 2067
Регистрация: 27.09.2012
Сообщений: 27,047
Записей в блоге: 1
27.06.2013, 15:54
Если вспомнить книгу Макконнелла, то если переменной при создании не задается значение и она содержит мусор, то это неверная инициализация
0
Комп_Оратор)
Эксперт по математике/физике
 Аватар для IGPIGP
9007 / 4708 / 630
Регистрация: 04.12.2011
Сообщений: 14,003
Записей в блоге: 16
27.06.2013, 16:23
Цитата Сообщение от Croessmah Посмотреть сообщение
неверная инициализация
Неверных инициализаций не бывает. То есть взаимно это как-то.
Вообще, для новичка такие вещи как объявление, определение и инициализация, - предварительное объявление, как и многое другое. Нельзя язык учить как букварь, многое можно понять значительно позже ознакомления.
@_Cherep_, объявление это информация для компилятора для формирования кода. С местом объявления связаны: время жизни, видимости, действия переменной, например.
Определение - информация компилятору и редактору связей для конкретизации значения или адреса.
Инициализация - совмещение, того и другого. Тема большая. Вам пока достаточно понять, что константы и ссылки, невозможно объявить без инициализации. А уж как работают конструктора при инициализации или присваивании это лучше читать и спрашивать конкретно.
0
Супер-модератор
Эксперт функциональных языков программированияЭксперт Python
 Аватар для Catstail
38228 / 21160 / 4314
Регистрация: 12.02.2012
Сообщений: 34,773
Записей в блоге: 14
27.06.2013, 16:47
В C++ есть такие понятия:

1) объявление (декларация)
2) определение (дефиниция)

Пояснить что есть что, проще всего на примере функций:

C++
1
2
3
4
5
6
7
8
9
10
11
12
13
int F1(int a);
{
    int i,j;
    ...
    j=F2(i);
 
    return ...
}
 
int F2 (int x)
{
 ...
}

Этот код не скомпилируется, т.к. в момент компиляции F1 компилятор ничего не знает про F2.
Чтобы код скомпилировался, функцию F2 нужно предварительно объявить (декларировать):

C++
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
int F2(int);  // Декларация F2
 
int F1(int a);
{
    int i,j;
    ...
    j=F2(i);
 
    return ...
}
 
int F2 (int x)  // Дефиниция F2 (определение)
{
 ...
}
Другой вариант: разместить определение F2 перед F1:

C++
1
2
3
4
5
6
7
8
9
10
11
12
13
int F2 (int x)  // Дефиниция F2 (определение)
{
 ...
}
 
int F1(int a);
{
    int i,j;
    ...
    j=F2(i);
 
    return ...
}
Теперь декларация не нужна (поскольку всякая дефиниция является одновременно и декларацией).

Ну, а инициализация - это присвоение объекту или переменной некоего значения в момент создания.
1
Неэпический
 Аватар для Croessmah
18150 / 10732 / 2067
Регистрация: 27.09.2012
Сообщений: 27,047
Записей в блоге: 1
27.06.2013, 16:47
@IGPIGP, Откопал у Макконнелла
Неверная инициализация данных - один из плодородных источников ошибок в программировании. Эффективные способы предотвращения проблем с инициализацией могут значительно ускорить отладку.
При неверной инициализации проблемы объясняются тем, что переменная имеет не то первоначальное значение, которое вы ожидаете. Это может случиться по одной из следующих причин.
- Переменной не было присвоено значения. Она имеет то случайное значение, которое находилось в соответствующих ячейках памяти при запуске программы.
- Значение переменной устарело. Когда-то переменной было присвоено значение, но оно утратило свою актуальность.
- Одним частям переменной были присвоены значения, а другим нет.
1
Комп_Оратор)
Эксперт по математике/физике
 Аватар для IGPIGP
9007 / 4708 / 630
Регистрация: 04.12.2011
Сообщений: 14,003
Записей в блоге: 16
27.06.2013, 17:43
Цитата Сообщение от Croessmah Посмотреть сообщение
Неверная инициализация данных - один из плодородных источников ошибок в программировании.
Это правда. Тем не менее может же быть случай когда переменная должна быть объявлена и не может быть проинициализирована полностью. Например если классы связны указателями друг на друга.
Новичку это ненужно. :
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
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
#include <iostream>
#include <string>
#include <typeinfo.h>
using namespace std;
class A {
int a;
double b;
string c;
public:
    A()
        :a(1), b(2.0), c("a anb b were sitting on a pipe")  
    {}
A(int a_)//частично инициализирует
:a(a_)
{}
A(double b_)//частично инициализирует
:b(b_)
{}
A(string c_)//частично инициализирует
:c(c_)
{}
A(const A& orig)//копирующий (и полностью инициализирующий)
:a(orig.a), b(orig.b), c(orig.c)
{}
    int& propertyA(){
return a;
}
    double& propertyB(){
return b;
}
string& propertyC(){
return c;
}
};
int main()
 {
     A *b=new A;//динамическая память выделена но не инициализирована
     cout<<b->propertyA()<<endl;//мусор если конструктор по умолчанию (без параметров) закоментирован
 
     A a;//память на стеке выделена
     cout<<a.propertyA()<<endl;////мусор если конструктор закоментирован
     a.propertyA()=2;// заполняется простым присваиванием
     a.propertyB()=5.0;// заполняется простым присваиванием
     a.propertyC()="a+b= ";// заполняется простым присваиванием
     
     cout<<a.propertyA()<<endl;
     cout<<a.propertyB()<<endl;
     cout<<a.propertyC()<<a.propertyA()+a.propertyB()<<endl;
 
     A c(a);//A c = a; - аналогично, полноценность инициализации определяется полноценность конструктора копии
 
     cout<<c.propertyA()<<endl;
     cout<<c.propertyB()<<endl;
     cout<<c.propertyC()<<a.propertyA()+a.propertyB()<<endl;
 
     A d = "Oi scolco musora budet esli razremite stroki nige...";//работает конструктор преобразования принимающий строку
     //остальные поля не инициализированы
     //отложенную, частичную инициализацию можно использовать для связывания двух экземпляров классов, когда
     //один из них обявлен опережающим объявлением, но не может быть полностью инициализирован без указателя на
     //второй, а второму для создания экземпляра нужен указатель на первый
     //такую штуку (создание пары связянных объектов разных классов можно описать в глобальном или статическом методе
     //или написать для этого отдельный класс.
     cout<<d.propertyC()<<endl;
     //cout<<d.propertyA()<<endl;
     //cout<<d.propertyB()<<endl;
     system("pause");
     }
0
:)
Эксперт С++
4773 / 3267 / 497
Регистрация: 19.02.2013
Сообщений: 9,046
27.06.2013, 17:49
Цитата Сообщение от IGPIGP Посмотреть сообщение
Например если классы связны указателями друг на друга.
В таком случае следует инициализировать неким нулевым значением, которое будет четко говорить, что поле не инициализировано. А не оставлять его в "мусорном" состоянии. Например должно быть как минимум так:
C++
1
2
3
A(int a_)//частично инициализирует
:a(a_), b(0) // c - не нужно, т.к. std::string инициализируется конструктором по умолчанию
{}
1
Неэпический
 Аватар для Croessmah
18150 / 10732 / 2067
Регистрация: 27.09.2012
Сообщений: 27,047
Записей в блоге: 1
27.06.2013, 17:55
Не нужно новичку?
Да ТС, наверное, уже в шоке от всей нашей писанины
1
Комп_Оратор)
Эксперт по математике/физике
 Аватар для IGPIGP
9007 / 4708 / 630
Регистрация: 04.12.2011
Сообщений: 14,003
Записей в блоге: 16
27.06.2013, 18:01
Цитата Сообщение от Tulosba Посмотреть сообщение
В таком случае следует инициализировать неким нулевым значением,
Может и правда. А если, ход выполнения одного из методов инициализации зависим от значения поля? Или поле - файловый поток, например?
Конечно если слить такие классы в один, то такой вопрос обходится, а если не нет? У меня маловато опыта, чтобы сказать определённо.

Добавлено через 4 минуты
Цитата Сообщение от Croessmah Посмотреть сообщение
Да ТС, наверное, уже в шоке от всей нашей писанины
Не может быть. Сейчас заметил: в заголовке typeinfo,h забыл удалить и вообще сырой кусок.
0
:)
Эксперт С++
4773 / 3267 / 497
Регистрация: 19.02.2013
Сообщений: 9,046
27.06.2013, 18:03
Цитата Сообщение от IGPIGP Посмотреть сообщение
А если, ход выполнения одного из методов инициализации зависим от значения поля?
Ради бога. Пусть зависит. Главное чтобы объект был в согласованном состоянии, т.е. сохранятся инвариант класса.
0
Комп_Оратор)
Эксперт по математике/физике
 Аватар для IGPIGP
9007 / 4708 / 630
Регистрация: 04.12.2011
Сообщений: 14,003
Записей в блоге: 16
27.06.2013, 18:39
Цитата Сообщение от Tulosba Посмотреть сообщение
Главное чтобы объект был в согласованном состоянии, т.е. сохранятся инвариант класса.
Это безопаснее конечно, но немного дольше. Разве нет?
0
Надоела реклама? Зарегистрируйтесь и она исчезнет полностью.
raxper
Эксперт
30234 / 6612 / 1498
Регистрация: 28.12.2010
Сообщений: 21,154
Блог
27.06.2013, 18:39

Объявления и определения структур
Может кто-нибудь объяснить как это работает: //Source1.cpp #include &quot;pch.h&quot; #include &lt;iostream&gt; using namespace std; ...

Циклы for. Проблема объявления/инициализации
Эх, так и придется создавать новую тему. А то, блин, интересно ж... Итак, я тут в недавней теме утверждал, что блок инициализации цикла...

Написать программу объявления, создания и инициализации двумерного прямоугольного массива
Написать программу объявления, создания и инициализации (при объявлении) двумерного прямоугольного массива, найти среднее арифметическое...

Когда выделяется память под переменные - во время объявления или инициализации
Привет! Вопрос такой: когда выделяется память под переменные - во время объявления или инициализации?

Архитектура правильного определения и объявления класса
Всем привет! В процессе написания одной программы &quot;поймал&quot; себя на том, что видимо не до конца понимаю логику правильного определения...


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

Или воспользуйтесь поиском по форуму:
40
Ответ Создать тему
Новые блоги и статьи
FPS контроллер с анимированными Y-Bot и 3D-звуком miniaudio (Box3D, Recast, BehaviorTree.CPP, ozz-animation, ImGui, OpenGL и SDL3)
8Observer8 18.10.2026
Содержание блога | English Version Полное мультиплатформенное руководство по стартовому проекту с FPS-контроллером игрока, анимированными роботами Y-Bot с 4-слойным блендингом, 3D-физикой Box3D,. . .
Локальный http сервер
Argus19 17.10.2026
Локальный http сервер На работе, на двух локальных компьютерах круглосуточно работают программы опроса приборов с записью в книги Excel,которые раз в сутки записываются на сервер компании. Т. к. . . .
Копировать Windows на новый диск на UEFI
damix 17.10.2026
https:/ / uriesk. wordpress. com/ 2016/ 11/ 01/ move-window-10-to-ssd-on-a-uefi-dualboot-system-with-basic-linux-tools/ TL DR Вставляем диск, а старый подключаем через переходник, грузимся с лайва. . .
ИИ не может найти нужный язык в списке
Supersumestria 05.10.2026
Я ему даю вот такое изображение и прошу найти и подчеркнуть немецкий язык. Возвращает он вот это: https:/ / i. **********/ vqBWLe2. png Нужную строчку в 3й колонке просто выдумал. . Это. . .
Новая последняя моя музыка в SUNO
zorxor 05.10.2026
Здравствуйте, дорогие мои друзья! С большой радостью я хотел бы представить вам свою новую последнею музыку, которую сгенерировала мне по моей просьбе нейросеть SUNO. С уважением, zorxor. Это. . .
Программный домашний кинотеатр
russiannick 27.09.2026
Сподобился на программный домашний кинотеатр. В качестве ЯВУ по традиции выбрал js. В помощники взял Яндекс-Алису. Было создано три зала на разные интересы. исторические и ретро сериал Хичкок. . .
Беседа с ИИ о программистах, недопускающих к созданию и правке кода генеративные ИИ и причины этого
zorxor 21.09.2026
Раньше я радовался или получал некоторые эмоции, пусть небольшие, но всё же, от самого процесса написания кода, рекомпиляции и запуска, видя постепенное развитие программы и прочее. А теперь лень. . .
Мобильное приложение ColorStep
pavlinmavlin 17.09.2026
Реализовал приложение Красный, Зеленый, Синий в Unity3d + c#. Название изменил на ColorStep. Приложение прошло модерацию и теперь доступно для скачивания. Делал его сам, шаг за шагом — и вот,. . .
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin
Copyright ©2000 - 2026, CyberForum.ru