|
|
  |
Вопросы по C от ламера, В книжках ответа чёта не нахожу |
|
|
Guest_Скопидор_*
|
Apr 10 2009, 11:16
|
Guests

|
Зачем вообще нужно ключевое слово «auto»? Ведь классификатор(или квалификатор? как это слово точно называется?) памяти «auto» никак не используется ( по крайней мере в исходниках разных разработчиков я его не видел). Т.к. глобальные переменные не могут быть « auto», а локальные и так по умолчанию «auto».
Сообщение отредактировал Скопидор - Apr 10 2009, 11:19
|
|
|
|
Guest_Скопидор_*
|
Apr 10 2009, 18:29
|
Guests

|
Цитата(SysRq @ Apr 10 2009, 17:37)  На Хабре было интересно: http://habrahabr.ru/blogs/cpp/25330/ (с подзаголовка "Ты где был, auto?"). " ... Спустя три десятка лет стандарт C++09 вновь вводит ключевое слово auto. Переменная, определённая под этим ключевым словом автоматически приобретёт тип при инциализации. ... "©Обана!  Ахринеть А в книжках Павловской и Подбельского об этом использовании ключевого слова "auto" ни звука P.S. Спасибо огромное за ответы, Господа mdmitry и SysRq.
Сообщение отредактировал Скопидор - Apr 10 2009, 18:31
|
|
|
|
Guest_Скопидор_*
|
Apr 10 2009, 22:02
|
Guests

|
Какие компиляторы (каких фирм) и начиная с какого года поддерживают ключевое слово "export" (т.е. экспорт шаблонов функций и классов)?
И есть ли Freeware компиляторы C++, с объёмом до 10МБ, которые ПОЛНОСТЬЮ поддерживают самый последний стандарт C++
Почему после того, как я вместо iostream.h стал юзать iostream объём экзешника вырос с 0.2МБ до почти о.5МБ?
|
|
|
|
Guest_Скопидор_*
|
Apr 14 2009, 20:40
|
Guests

|
Цитата(Student Pupkin @ Apr 13 2009, 23:15)  Но я думал, что по общепринятым правилам следовало в одном из модулей обявить все эти глобальные переменные обычным образом, а в остальных - с квалификатором extern... Дык объявлять каждую переменную в каждом из N модулей запарисся. Да и вероятность ошибки возрастает ................................................................................ ....... А Вы, BSVi, Сами себе противоречите. С одной стороны Вы пишите: Цитата(BSVi @ Apr 14 2009, 10:36)  ... внимание, в заголовках нельзя обьявлть переменные. кроме констант А с другой пишите: Цитата(BSVi @ Apr 14 2009, 10:36)  ... переменные .... лучше сделать отдельным модулем global_vars.c и global_vars.h А разве global_vars.h - это не заголовочный файл?
Сообщение отредактировал Скопидор - Apr 14 2009, 20:41
|
|
|
|
Guest_Скопидор_*
|
Apr 14 2009, 21:42
|
Guests

|
Цитата(ukpyr @ Apr 15 2009, 01:23)  правильно, в хидере каждого модуля обьявляются публичные переменные, видимые в других модулях. Подключаем .h файл - и получаем доступ к публичным переменным. А в .с файле модуля объявляются внутренние переменные модуля. А как из файла main_1.c я получу доступ к "публичным" переменным файла "main_2.h"?
Сообщение отредактировал Скопидор - Apr 14 2009, 21:44
|
|
|
|
Guest_Скопидор_*
|
Apr 14 2009, 22:13
|
Guests

|
1.А обязательно ли в препроцессорной директиве #include использовать файлы с расширением .h ? Т.е. могу ли, например, написать файл с раширением .my и вложить его содержимое в основной файл с помощью директивы #include? 2. Почему директиву #include используют в начале файла? А существуют ли случаи, когда выгодно использовать эту директиву в середине, или даже в конце основного файла? И что это за случаи? 3. Использование #include подразумевает экспортирование ресурсов из .h-файла. А бывают ли случаи, когда наоборот, вкладываемый файл импортирует ресурсы из того файла, в который он вкладывается? Если да, то что это за случаи? Цитата(andrew_b @ Apr 13 2009, 09:32)  Думаю, вам лучше обратиться на более специализированный ресурс. На RSDN, например. Ссылка битая. Сайт не грузится 4. Есть прога: Код void main(void) { int I = 1; { // блок2 int I = 2; goto Exit; // --------------- I++; } I = 4; // ------------------ Exit:; I = 3; } На входе в блок2, я так понимаю, компилятор сохранит в стеке регистровый контекст и выделит в стеке память под локальную переменную I. А на выходе компилятор должен будет восстановить контекст (в том числе указатель стека), который был непосредственно перед входом в блок2. Но т.к. выполняется команда перехода за пределы блока2, то получается, что команды восстановления контекста из стека будут пропущены? 5.Если main – функция, то можно ли её рекурсивно вызвать внутри её самой? 6. Как избежать в своей программе непреднамеренного «экранирования» идентификаторов из стандартной библиотеки?
Сообщение отредактировал Скопидор - Apr 14 2009, 22:17
|
|
|
|
|
Apr 14 2009, 23:32
|

Чайник, 1 литр
   
Группа: Свой
Сообщений: 655
Регистрация: 17-05-06
Из: Moscow
Пользователь №: 17 168

|
Цитата(Скопидор @ Apr 11 2009, 02:02)  Почему после того, как я вместо iostream.h стал юзать iostream объём экзешника вырос с 0.2МБ до почти о.5МБ? wcin, wcout... Цитата(Скопидор @ Apr 15 2009, 02:13)  А обязательно ли в препроцессорной директиве #include использовать файлы с расширением .h ? Нет. Часто применяется, к примеру, .hpp. Аналогия C -- .c, C++ -- .cpp. Цитата(Скопидор @ Apr 15 2009, 02:13)  ...когда выгодно использовать эту директиву в середине, или даже в конце основного файла? Когда выгодно! Скажем, изменить макрос какой-нить, используемый в исходнике, вставив .h-файл с ifdef-undef-define этого макроса в середину исходника, и пусть враги догадываются почему мой спёртый ими исходник у них не работает. Цитата(Скопидор @ Apr 15 2009, 02:13)  Использование #include подразумевает экспортирование ресурсов из .h-файла. А бывают ли случаи, когда наоборот... Неверное понятие сути, нет там экспортирования никакого. Это паззл, если хотите  Цитата(Скопидор @ Apr 15 2009, 02:13)  Если main – функция, то можно ли её рекурсивно вызвать внутри её самой? Зависит от того, как она определена, от атрибутов ее. Сохранение контекста и прочее... Цитата(Скопидор @ Apr 15 2009, 02:13)  Как избежать в своей программе непреднамеренного «экранирования» идентификаторов из стандартной библиотеки? Читать документацию на используемые бибилиотеки.
|
|
|
|
Guest_Скопидор_*
|
Apr 15 2009, 00:48
|
Guests

|
Цитата(SysRq @ Apr 15 2009, 03:32)  Неверное понятие сути, нет там экспортирования никакого. Это паззл, если хотите  Ну как же. Например, я могу описать в h-файле прототип функции f1 и юзать его внутри тела функции f2, которая определена в h-файле. А вот конкретная реализация f1 будет содержаться в файле, в который будет вложен h-файл, т.е. как бы будет импортироваться из основного файла. Т.е. получается, что реализация f2 будет зависеть от того, куда будет вложен h-файл. Цитата(SysRq @ Apr 15 2009, 03:32)  Зависит от того, как она определена, от атрибутов ее. Сохранение контекста и прочее... Т.е. в принципе возможно юзать вызовы main внутри тела main? Цитата(SysRq @ Apr 15 2009, 03:32)  Читать документацию на используемые бибилиотеки. И больше никак? Т.е. я при выборе каждого идентификатора в своей проге должен смотреть: «а нет ли точно такого же идентификатора в стандартной библиотеке». Так? А насчёт перепрыгивания участка восстановления контекста из стека что скажете?
|
|
|
|
|
Apr 15 2009, 01:45
|

Чайник, 1 литр
   
Группа: Свой
Сообщений: 655
Регистрация: 17-05-06
Из: Moscow
Пользователь №: 17 168

|
Цитата(Скопидор @ Apr 15 2009, 04:48)  Ну как же. Срочно читать как из .cpp получается .exe. Цитата(Скопидор @ Apr 15 2009, 04:48)  Т.е. в принципе возможно юзать вызовы main внутри тела main? Можно. Поищите еще "точка входа". Цитата(Скопидор @ Apr 15 2009, 04:48)  Т.е. я при выборе каждого идентификатора в своей проге должен.. Вы какой язык изучать собрались? C++? Инкапсуляция, наследование, и т.п. -- туда читайте. Вопрос отпадет. О глобальных переменных флудить не будем, тема уже была, ищите на форуме. Как правило хорошего тона afaik не следует использовать _такие и __такие вот идентификаторы в прикладной программе. Цитата(Скопидор @ Apr 15 2009, 04:48)  А насчёт перепрыгивания... За goto - секирбашка. Особенно в C++. Флудить не будем, тема уже была тоже.
|
|
|
|
|
Apr 15 2009, 04:31
|

Беспросветный оптимист
     
Группа: Свой
Сообщений: 4 640
Регистрация: 26-12-07
Из: Н.Новгород
Пользователь №: 33 646

|
Цитата(Скопидор @ Apr 15 2009, 02:13)  Есть прога: ... На входе в блок2, я так понимаю, компилятор сохранит в стеке регистровый контекст C чего бы это вдруг? Цитата и выделит в стеке память под локальную переменную I. А на выходе компилятор должен будет восстановить контекст (в том числе указатель стека), который был непосредственно перед входом в блок2. Никому он ничего не должен. Блок {} означает всего лишь составной оператор, никаких переходов и контекстов не имеется в виду.
Причина редактирования: Излишнее цитирование.
--------------------
Программирование делится на системное и бессистемное. ©Моё :) — а для кого-то БГ — это Bill Gilbert =)
|
|
|
|
|
Apr 15 2009, 04:41
|
Профессионал
    
Группа: Свой
Сообщений: 1 975
Регистрация: 30-12-04
Из: Воронеж
Пользователь №: 1 757

|
Цитата(Скопидор @ Apr 15 2009, 02:13)  1.А обязательно ли в препроцессорной директиве #include использовать файлы с расширением .h ? Т.е. могу ли, например, написать файл с раширением .my и вложить его содержимое в основной файл с помощью директивы #include? Да. Расширение вообще ни причём. См. ниже. Цитата 3. Использование #include подразумевает экспортирование ресурсов из .h-файла. Ничего подобного. #include -- это просто включение текста одного файла в другой файл. Ничего больше. Почитайте про препроцессор. Цитата Ссылка битая. Сайт не грузится Ссылка не битая. А сайт действительно не грузится. С ним это бывает крайне редко. Попробуйте попозже. Это лучший ресурс в рунете по программированию.
|
|
|
|
Guest_Скопидор_*
|
Apr 15 2009, 07:30
|
Guests

|
Цитата(andrew_b @ Apr 15 2009, 08:41)  Ничего подобного. #include -- это просто включение текста одного файла в другой файл. Да я в курсе. Просто я говорил о том, что можно код распределить по файлам так, что не CPP-файл будет юзать ресурсы из H-файла, а наоборот. И это будет выглядеть как импортирование. Приведу пример CODE // Файл f.h int I,J; int F1(int, int); // Прототип функции, реализация которой будет определена в C-файле int F2(void); // Функция, которая использует F1 { return (F1(I,J)); }
// Файл main1.c #include "f.h " int Result; // -------------------- int F1( int A, B) { return (A*B) } // -------------------- void main (void) { I = 3; J = 4; Result = F2(); } // --------------------
// Файл main2.c #include "f.h " int Result; // -------------------- int F1( int A, B) { return (A+B) } // -------------------- void main (void) { I = 3; J = 4; Result = F2(); } // -------------------- Вот и получается, что алгоритм работы определённой в файле f.h функции F2 зависит от того, в какой файл будет вложен f.h: в main1.c или в main2.c. Т.е. всё выглядит так, что как будто бы в функцию F1 импортируется реализация из C-файла, т.к. результат, возвращаемый функцией F1 (а значит и использующей её F2) зависит от того, в какой файл был вложен f.h. Цитата(andrew_b @ Apr 15 2009, 08:41)  Да. Расширение вообще ни причём. См. ниже. А я вот когда работал в WinAVR, то там при создании проекта создаются категории Header и Source. И если включить файл *.h в категорию Header, то можно даже в исходнике не писать #include *.h. Так как компилятор сам поймёт что *.h файл нужно вложить во все исходники проекта (во все *.c файлы). Или я не прав? Вот я и думаю, что если у меня файл, включнённый в категорию Header будет иметь расширение не h, а другое? "Подцепит" ли его компилятор автоматом к проекту?
Причина редактирования: Уменьшение видимого размера цитаты исходника.
|
|
|
|
|
Apr 15 2009, 07:41
|

Беспросветный оптимист
     
Группа: Свой
Сообщений: 4 640
Регистрация: 26-12-07
Из: Н.Новгород
Пользователь №: 33 646

|
Цитата(Скопидор @ Apr 15 2009, 11:30)  И если включить файл *.h в категорию Header, то можно даже в исходнике не писать #include *.h. Так как компилятор сам поймёт что *.h файл нужно вложить во все исходники проекта (во все *.c файлы). Хрень какую-то несёте в массы. Компилятор не может ничего никуда автоматом "подцеплять". Он может тупо компилить, что ему дадут. Максимум что может быть, так это что ваши h-файлы будут видны из любого места проекта, и можно будет инклудить их просто #include "some_header.h" без указания абсолютного пути. Опять же, к компилятору это никаким боком, это делает утилита, формирующая makefile.
Причина редактирования: Излишнее цитирование.
--------------------
Программирование делится на системное и бессистемное. ©Моё :) — а для кого-то БГ — это Bill Gilbert =)
|
|
|
|
Guest_Скопидор_*
|
Apr 15 2009, 07:47
|
Guests

|
Цитата(SysRq @ Apr 15 2009, 05:45)  Срочно читать как из .cpp получается .exe. В 2 этапа: сначала по отдельности компилируем все файлы (получаем OBJ-файлы), потом линкуем. Правильно? Цитата(SysRq @ Apr 15 2009, 05:45)  Вы какой язык изучать собрались? C++? Инкапсуляция, наследование, и т.п. -- туда читайте. Вопрос отпадет. О глобальных переменных флудить не будем, тема уже была, ищите на форуме. Т.е. если «очень постараться» (  ) (ну не внимательно подойти к выбору идентификаторов в своей программе), то всё же есть вероятность «наступить на грабли» и случайно экранировать идентификаторы из стандартной библиотеки в своей проге? Я не говорю сейчас о своих идентификаторах, начинающихся на _, __ или заканчивающихся на _t. Допустим, к примеру, я такой дуб, что не знал, что в библиотеке уже юзаются cin и cout. И взял, и переопределил их в своей проге. Может такое быть? Цитата(SysRq @ Apr 15 2009, 05:45)  За goto - секирбашка. Особенно в C++. Флудить не будем, тема уже была тоже. Да я не собираюсь флудить, нужен или не нужен goto. Просто хотел узнать как это реализуется: осуществляется «прыжок» за пределы блока и при этом, КАК-ТО, восстанавливается контекст, сохранённый на входе в блок. P.S. Прошу прощения, если мои вопросы кажутся глупыми, я ж говорю, я ламер.
|
|
|
|
|
Apr 15 2009, 07:54
|

Нечётный пользователь.
     
Группа: Свой
Сообщений: 2 033
Регистрация: 26-05-05
Из: Бровари, Україна
Пользователь №: 5 417

|
Цитата(Скопидор @ Apr 15 2009, 10:44)  Допустим, к примеру, я такой дуб, ... Может такое быть? Запросто. Но достаточно либо определить свои cin/cout в своём пространстве имён oak и квалифицировать при использовании oak::cin либо не переносить сущности стандартной библиолтеки в глобальное пространство имён, что происходит при использовании Код #include <iostream.h> вместо Код #include <iostream> или при совсем глобальном переносе Код using namespace std; В этом случае к "стандартно-библиотечным" придётся обращаться как к std::cin, но они тоже не пересекутся с новоявленными. А вообще поломать можно что угодно.
--------------------
Ну, я пошёл… Если что – звоните…
|
|
|
|
Guest_Скопидор_*
|
Apr 15 2009, 08:09
|
Guests

|
Цитата(MrYuran @ Apr 15 2009, 11:41)  Хрень какую-то несёте в массы. Ну когда мы делаем "add File to Project" мы же хидеры добваляем в категорию "Header". И после того как файл проекта (dsn по-моему) сформирован, компилятор знает, какие *.h файлы юзать при сборке. Разве не так? Цитата(MrYuran @ Apr 15 2009, 08:31)  C чего бы это вдруг?  Никому он ничего не должен. Блок {} означает всего лишь составной оператор, никаких переходов и контекстов не имеется в виду. А я прочитал в книшшке, что если внутри {…} определяются локальные переменные, то составной оператор автоматом становиться блоком со всеми вытекающими последствиями (сохранение контекста процессора при входе в блок, создание локальных переменных в стеке и т.п.) Цитата(ReAl @ Apr 15 2009, 11:54)  определить свои cin/cout в своём пространстве имён oak и квалифицировать при использовании oak::cin А что такое «oak»? …. Т.е. Ваше сообщение было к тому, что «сломать» очень сложно? Но ведь стандартная библиотека – это не только классы и шаблоны.
Причина редактирования: Излишнее цитирование.
|
|
|
|
|
Apr 15 2009, 08:19
|
Профессионал
    
Группа: Свой
Сообщений: 1 975
Регистрация: 30-12-04
Из: Воронеж
Пользователь №: 1 757

|
Цитата(ReAl @ Apr 15 2009, 11:54)  Так это давным-давно deprecated. Цитата(Скопидор @ Apr 15 2009, 12:09)  Ну когда мы делаем "add File to Project" Ну и при чём тут компилятор. Цитата мы же хидеры добваляем в категорию "Header". И после того как файл проекта (dsn по-моему) сформирован, компилятор знает, какие *.h файлы юзать при сборке. Разве не так? Компилятор про проект ничего не знает.
|
|
|
|
|
Apr 15 2009, 08:30
|

Нечётный пользователь.
     
Группа: Свой
Сообщений: 2 033
Регистрация: 26-05-05
Из: Бровари, Україна
Пользователь №: 5 417

|
Цитата(Скопидор @ Apr 15 2009, 10:47)  Да я не собираюсь флудить, нужен или не нужен goto. Просто хотел узнать как это реализуется: осуществляется «прыжок» за пределы блока и при этом, КАК-ТО, восстанавливается контекст, сохранённый на входе в блок. Обычно ничего никуда не сохраняется и не восстанавливается в таких блоках. Код voif foo() { int i = 0; { char c; ... } ++i; { long l; ... } --i; } Компилятор анализирует всю функцию и в исполняемом коде уже на входе в функцию на стеке резервируется, грубо говоря Код struct { int i; union { char c; long l; }; } local_variables; и больше стек туда-сюда не дёргается, просто происходит использование места на стеке в соответствии с деревом вложенных блоков кода. При минимальной современной оптимизации ещё и происходит анализ использования переменных и если какая-то используется до середины и дальше не нужна, а какая-то другая наоброт - используется только от середины (первое использование после последнего использования той), то они тоже накладываются в стеке для экономии его размера. При этом переход по goto ничего не ломает (если он не обходит инициализацию переменной при попадании на метку, т.е. вопросы не к точке прыжка goto, а к точке приземления), так как структура/объединение на стеке остаются неподвижными, меняется только интерпретация. Естественно, это так просто только для типов без конструкторов/деструкторов. Особенно учитывая то, что во вложенных вызовах могут произойти исключения, которые подействуют "аналогично goto" с точки зрения этих объектов, а при отсутствии в данной функции try/catch её вообще всё "прошьёт". Поэтому для них в стековых кадрах функций устраиваются записи о деструкторах, которые необходимо выполнить при выходе из блока и порядке этих вызовов, при выходе из любого блока по goto/return/исключению просматриваются эти записи и вызываются необходимые деструкторы для автоматических объектов в блоках (unwind). Код #include <iostream>
class FOO { public: FOO(int i_) : i(i_) { std::cout << __PRETTY_FUNCTION__ << " (" << i << ")\n"; } ~FOO() { std::cout << __PRETTY_FUNCTION__ << " (" << i << ")\n"; } private: int i; };
int main(int ac, char **av) { FOO f1(1); { FOO f2(2); if(ac == 1) goto aaa; // в случае перехода даже не сконструируется, но место на стеке под поле i зарезервировано заранее FOO f3(3); } aaa:; } Вызываем с аргументом в командной строке (goto не выполняется) Цитата FOO::FOO(int) (1) FOO::FOO(int) (2) FOO::FOO(int) (3) FOO::~FOO() (3) FOO::~FOO() (2) FOO::~FOO() (1) Вызываем без аргумента Цитата FOO::FOO(int) (1) FOO::FOO(int) (2) FOO::~FOO() (2) FOO::~FOO() (1) Цитата(Скопидор @ Apr 15 2009, 11:09)  А что такое «oak»? http://www.abbyyonline.ru/Translate.aspx?l...1&words=oakМожете для своих вещей выбрать другое имя. Можете несколько, для разных частей проекта свои. Цитата(Скопидор @ Apr 15 2009, 11:09)  Т.е. Ваше сообщение было к тому, что «сломать» очень сложно? Но ведь стандартная библиотека – это не только классы и шаблоны. Оно к тому, что в языке есть средства для того, чтобы можно было не ломать. Цитата(andrew_b @ Apr 15 2009, 11:19)  Так это давным-давно deprecated. У меня просто до сих пор в ходу mingw32-gcc 3.4.2 пятилетней давности, у него в backward/ ещё болтается всё
--------------------
Ну, я пошёл… Если что – звоните…
|
|
|
|
Guest_Скопидор_*
|
Apr 15 2009, 08:39
|
Guests

|
Цитата(andrew_b @ Apr 15 2009, 12:19)  Ну и при чём тут компилятор. Компилятор про проект ничего не знает. А для кого тогда создаётся DSN-файл? ..................................... ..................................... ..................................... ReAl!! Спасибо за столь развёрнутый и подробный ответ. Я его весь пока не асисилил, но работаю над этим  Т.е. как я понял, компилятор выделяет память под все локальные переменные любого уровня вложенности блоков на входе в функцию? Т.е. если в функции описана переменная i, а во вложенном в функцию блоке – переменная j, то память в стеке и под i и под j будет выделена на входе в функцию, а уничтожена на выходе по команде return?
Сообщение отредактировал Скопидор - Apr 15 2009, 08:42
|
|
|
|
Guest_Скопидор_*
|
Apr 15 2009, 10:09
|
Guests

|
Цитата(andrew_b @ Apr 15 2009, 13:11)  Видимо, для IDE. IDE != компилятор. Но ведь эта IDE позволяет не писать в каждом файле #include ..., т.е. берёт на себя функции компилятора?
|
|
|
|
Guest_Скопидор_*
|
Apr 15 2009, 15:42
|
Guests

|
Вопрос №7.
Можно ли использовать при объявлении (описании или определении) переменной использовать идентификатор типа, который будет опредёлён ниже или в другом файле? И как это сделать?
============================ Вопрос №8.
Вопрос по typedef.
Зачем писать так: typedef unsigned int UINT Если можно так: #define UINT (unsigned int)
В чём принципиальная разница?
================================== Вопрос №9.
Можно ли в C++ заставить компилятор АВТОМАТИЧЕСКИ генерировать код, контролирующий выход результатов вычислений за пределы допустимого диапазона? Есть ли для этого какие-то специальные ключи компиляции?
Допустим, есть такой фрагмент кода:
unsigned short int i , j , k ; … k = i + j // что будет если (i+j) > 65535?
============================ Вопрос №10.
Для чего нужно ключевое слово «signed» если оно никогда на практике не используется?
============================== Вопрос №11.
Зачем нужны две формы инициализации переменной?
int i = 10 и int i(10)
В чём между ними принципиальная разница?
Сообщение отредактировал Скопидор - Apr 15 2009, 15:44
|
|
|
|
|
Apr 15 2009, 20:00
|

Чайник, 1 литр
   
Группа: Свой
Сообщений: 655
Регистрация: 17-05-06
Из: Moscow
Пользователь №: 17 168

|
Цитата(Скопидор @ Apr 15 2009, 19:42)  ...идентификатор типа, который будет опредёлён ниже или в другом файле? Тип должен быть известен (прототип, или еще как-либо; declaration). Известным тип так же считается, если вы как раз его и описываете (простейший пример - свзяный список структур: в структуре при ее обявлении есть указатель на неё же). Цитата(Скопидор @ Apr 15 2009, 19:42)  Зачем писать так: typedef unsigned int UINT Код #define int_pointer int * int_pointer myint1, myint2; После подстановки препроцессором: Код int *myint1, myint2; // первое - указатель, а второе-то вовсе нет; а с typedef все будет правильно Цитата(Скопидор @ Apr 15 2009, 19:42)  ...АВТОМАТИЧЕСКИ генерировать код, контролирующий выход результатов вычислений за пределы допустимого диапазона? k = i + j // что будет если (i+j) > 65535? Хороший компилятор выдаст предупреждение о возможном переполнении. Будет отброшено то что не влезает, старшие биты. Цитата(Скопидор @ Apr 15 2009, 19:42)  Для чего нужно ключевое слово «signed» если оно никогда на практике не используется? По-умолчанию char в WinAVR (и не только) считается unsigned (опция компилятора). Использовать signed - единственный способ заставить его в таком случае работать как со знаковой. Цитата(Скопидор @ Apr 15 2009, 19:42)  int i = 10 и int i(10) Присваивание значения либо через оператор =, или через конструктор.
|
|
|
|
Guest_Скопидор_*
|
Apr 15 2009, 20:34
|
Guests

|
Цитата(SysRq @ Apr 16 2009, 00:00)  Присваивание значения либо через оператор =, или через конструктор. А когда лучше какую из форм юзать? P.S. И ещё. Насколько я понял форму инициализации со скобками можно юзать только для локальных переменных. Почему?
Причина редактирования: Нарушение п.3.4 Правил форума.
|
|
|
|
|
Apr 15 2009, 21:52
|

неотягощённый злом
     
Группа: Свой
Сообщений: 2 746
Регистрация: 31-01-08
Из: Санкт-Петербург
Пользователь №: 34 643

|
Цитата(Скопидор @ Apr 16 2009, 00:34)  А когда лучше какую из форм юзать? Через конструктор с аргументом. Т.к произойдёт создание переменной с одновременной инициализацией, а в другом случае будет два хода, создание переменной со значением по умолчанию (если оно есть) и только потом присвоение ей значения через оператор =, который реализуется обычно посредством конструктора копирования. Даже наверное хуже: создание переменной со значением по умолчанию, создание переменной с желаемым значением копирование одного в другое, удаление временной переменной... Писать на С++ можно начинать предварительно прочитав несколько штук весьма занимательных книжек  Помимо Бьёрна Страуструпа, очень рекомендую эти две книжечки: Скотт Майерс Эффективное использование С++ 50 способов и вторая часть 35 способов: http://www.bookvoed.ru/searching_for_shop276755.htmlЯ читал и плакал
--------------------
“Будьте внимательны к своим мыслям - они начало поступков” (Лао-Цзы)
|
|
|
|
|
Apr 16 2009, 04:48
|
Профессионал
    
Группа: Свой
Сообщений: 1 975
Регистрация: 30-12-04
Из: Воронеж
Пользователь №: 1 757

|
Цитата(Скопидор @ Apr 15 2009, 19:42)  Вопрос №10. Для чего нужно ключевое слово «signed» если оно никогда на практике не используется? Не надо обощать. Если вы его не используете, то это не значит, что другие не используют тоже. Как быть с отрицательными числами? Цитата(SysRq @ Apr 16 2009, 00:00)  Тип должен быть известен (прототип, или еще как-либо; declaration). Известным тип так же считается, если вы как раз его и описываете (простейший пример - свзяный список структур: в структуре при ее обявлении есть указатель на неё же). Ну, это всё-таки указатель, а не сама структура. Размер указателя всегда известен. А размер структуры -- только после того, как она будет полностью описана. Нпример, вы не можете написать: Код struct foo; struct bar { struct foo; };
|
|
|
|
|
Apr 16 2009, 10:35
|
;
     
Группа: Участник
Сообщений: 5 646
Регистрация: 1-08-07
Пользователь №: 29 509

|
Цитата(Скопидор @ Apr 15 2009, 18:42)  Вопрос №10. Для чего нужно ключевое слово «signed» если оно никогда на практике не используется? Хороший пример: Код typedef signed char int8_t; Но знаковость char по умолчанию можно задать еще и в командной строке! Ясное дело, отдавать себя на откуп памаметрам ком строки никто не согласится.
|
|
|
|
Guest_Скопидор_*
|
Apr 23 2009, 12:22
|
Guests

|
Возвращаясь к обсуждению директивы #include.
В некоторых книжках (вроде даже сам Страусс) пишут, что «единицей компиляции» является файл и что программа на C++ может состоять из нескольких файлов-исходников и что имеет место быть «раздельная компиляция». Т.е. файлы компилируются по отдельности и получается несколько OBJ-файлов, а затем эти «объектники» линкуются в один экзешник.
А если исходить из идеологии «include», то получается, что сначала препроцессор собирает из нескольких исходников один единственный исходник, и это ОДИН (!!!) файл компилируется.
Поясните мне это противоречие.
А потом, когда мы пишем, к примеру, #include <iostream> ведь не вставляется же сам исходный текст системного библиотечного файла в файл юзверя? Поскольку этого исходного текста нет в дистрибутиве (особенно если компилятор коммерческий), а есть его некий объектный код. Так?
Или я не прав?
Т.е. объясните мне как компилятор узнаёт когда нужно вставить текст в исходник, а когда нужно присоединить объектник файла уже на фазе линковки
Сообщение отредактировал Скопидор - Apr 23 2009, 11:34
|
|
|
|
|
Apr 23 2009, 12:23
|
Профессионал
    
Группа: Свой
Сообщений: 1 975
Регистрация: 30-12-04
Из: Воронеж
Пользователь №: 1 757

|
Цитата(Скопидор @ Apr 23 2009, 15:28)  Поясните мне это противоречие. Нет противоречия. Компилируется результат препроцессинга. А это один файл. Цитата А потом, когда мы пишем, к примеру, #include <iostream> ведь не вставляется же сам исходный текст системного библиотечного файла в файл юзверя? Поскольку этого исходного текста нет в дистрибутиве (особенно если компилятор коммерческий), а есть его некий объектный код. Так? Вы бы что ли ради интереса в этот файл заглянули. Цитата(Скопидор @ Apr 23 2009, 16:22)  Т.е. объясните мне как компилятор узнаёт когда нужно вставить текст в исходник, а когда нужно присоединить объектник файла уже на фазе линковки Препроцессор, компилятор и линкер -- это разные программы.
|
|
|
|
Guest_Скопидор_*
|
Apr 23 2009, 12:29
|
Guests

|
Дык всё-таки "раздельная компиляция" есть такое понятие? Или это всё домыслы манагеров и что реально компилиться всегда один CPP-исходник?
|
|
|
|
|
Apr 23 2009, 12:35
|
Профессионал
    
Группа: Свой
Сообщений: 1 975
Регистрация: 30-12-04
Из: Воронеж
Пользователь №: 1 757

|
Цитата(Скопидор @ Apr 23 2009, 16:29)  Дык всё-таки "раздельная компиляция" есть такое понятие? Да, есть. Цитата реально компилится всегда один CPP-исходник? Да.
|
|
|
|
Guest_Скопидор_*
|
Apr 23 2009, 12:35
|
Guests

|
Цитата(MrYuran @ Apr 23 2009, 16:27)  Код из библиотек не подставляется при компиляции, а линкуется при конечной сборке. А мне сказали, что препроцессор - это отдельная прога. Откуда она знает какой файл из библиотеки, а какой нет?
|
|
|
|
|
Apr 23 2009, 12:37
|

Беспросветный оптимист
     
Группа: Свой
Сообщений: 4 640
Регистрация: 26-12-07
Из: Н.Новгород
Пользователь №: 33 646

|
Цитата(Скопидор @ Apr 23 2009, 16:29)  Дык всё-таки "раздельная компиляция" есть такое понятие? Или это всё домыслы манагеров и что реально компилиться всегда один CPP-исходник? Ну если он один, то да. Если два - то сначала один, потом другой. Если три - то сначала один, потом второй, потом третий. И т.д. И всё это в соответствии с makefile -ом или опциями командной строки
--------------------
Программирование делится на системное и бессистемное. ©Моё :) — а для кого-то БГ — это Bill Gilbert =)
|
|
|
|
Guest_Скопидор_*
|
Apr 23 2009, 12:51
|
Guests

|
Т.е. препроцессор каким-то чудесным образом узнаёт в каких случаях при встрече им директивы #include вставлять вместо #include содержимое файла, а когда нет? А если он не вставляет содержимое системного файла в наш исходник, то почему компилятор не ругается "undefined variable" если мы юзаем переменные из системного файла? Цитата(MrYuran @ Apr 23 2009, 16:27)  Код из библиотек не подставляется при компиляции А тогда зачем вообще писать, к примеру, #include <iostream> если препроцессор всё равно не подставляет код из этого библиотечного файла в наш исходник?
Сообщение отредактировал Скопидор - Apr 23 2009, 13:07
|
|
|
|
|
Apr 23 2009, 12:54
|
Частый гость
 
Группа: Свой
Сообщений: 96
Регистрация: 16-11-05
Из: г.Екатеринбург
Пользователь №: 10 930

|
Цитата(Скопидор @ Apr 23 2009, 18:35)  А мне сказали, что препроцессор - это отдельная прога. Откуда она знает какой файл из библиотеки, а какой нет?  Где какой файл он узнаёт из путей, которые ему указывают. Если это кавычки (двойные или одинарные,не помню),то ищется в текущей директории проекта. Если угловые скобки, то в директориях, где сидят библиотеки, компиляторы, линкеры, т.е. иначе - системные директории. Пути прописываются в настройках компилятора, линкера, или препроцессора, или в среде разработки, смотря в чём вы работаете.
|
|
|
|
Guest_Скопидор_*
|
Apr 23 2009, 13:03
|
Guests

|
Цитата(AndreyKeil @ Apr 23 2009, 16:54)  Где какой файл он узнаёт из путей, которые ему указывают. Если это кавычки (двойные или одинарные,не помню),то ищется в текущей директории проекта. Если угловые скобки, то в директориях, где сидят библиотеки, компиляторы, линкеры, т.е. иначе - системные директории. Пути прописываются в настройках компилятора, линкера, или препроцессора, или в среде разработки, смотря в чём вы работаете. Т.е. работа препроцессора (вставлять содержимое файла в наш файл или не вставлять) зависит от того, в какой директории находится файл указанный в #include?
|
|
|
|
|
Apr 23 2009, 13:21
|

Начинающий профессионал
    
Группа: Свой
Сообщений: 1 215
Регистрация: 25-10-06
Из: СПб
Пользователь №: 21 648

|
Цитата(Скопидор @ Apr 23 2009, 17:03)  Т.е. работа препроцессора (вставлять содержимое файла в наш файл или не вставлять) зависит от того, в какой директории находится файл указанный в #include? Вставлять всегда, а искать этот файл сначала в зависимости от скобок. <> ищется сначала в системных файлах, затем в тех каталогах, которые указаны в настойках, включая каталог проекта. А чего рассуждать. Берете свой проект, в какой-то исходный файл пишите #include на несуществующий. Далее компиляция и разбор полетов. Очень наглядно  Использование препроцессора позволяет часто найти свои ошибки в #define. P.S. Может документацию по используемому Вами компилятору почитать, да и в книгах по С, CPP обычно использование препроцессора, компилятора, линкера и библиотекаря разбирается.
--------------------
Наука изощряет ум; ученье вострит память. Козьма Прутков
|
|
|
|
Guest_Скопидор_*
|
Apr 23 2009, 14:57
|
Guests

|
Вопрос №12Как и для чего в C++ используется идентификатор типа в enum кроме объявления/определения переменных? Код // main.cpp // 18:17 23 апреля 2009 г. #include <iostream> using namespace std; void main () { enum My_Type {null, one, two, three}; My_Type A; A = My_Type (10); // Почему здесь компилятор не ругается? Ведь 10 не входит в множество значений типа My_Type cout << "A = " << A << '\n'; // Пишет A = 10, хотя 10 больше самой большой из констант описанных в enum типа My_Type } /////////////////////////////////////////////////// /////////////////////////////////////////////////// Цитата(mdmitry @ Apr 23 2009, 17:21)  Вставлять всегда ??? А как же такие понятия как "раздельная компиляция" и "предкомпилированные файлы библиотек"? А как же высказывания участника: Цитата(MrYuran @ Apr 23 2009, 16:27)  Код из библиотек не подставляется при компиляции, а линкуется при конечной сборке. /////////////////////////////////////////////////// /////////////////////////////////////////////////// Вопрос №13 (Про функцию main)
В книгах по C++ вначале пишут что выполнение программы начинается с функции main. Но в главах, посвящённых классам, пишут что выполнение программы начинается с выполнения конструкторов объектов глобальных классов. Так с чего же всё-таки начинается выполнения программы?////////////////////////////////////////////////////////// Вопрос №14
В книгах по C++ пишут, что в строковых литералах допустимы почти любые символы. А какие символы не допустимо использовать внутри строкового литерала?Замечание модератора. Скопидор, Вы начинаете злоупотреблять возможностями по форматированию текста сообщения, нарушая п.2.1г Правил форума.
|
|
|
|
|
Apr 23 2009, 15:09
|

Беспросветный оптимист
     
Группа: Свой
Сообщений: 4 640
Регистрация: 26-12-07
Из: Н.Новгород
Пользователь №: 33 646

|
Цитата(Скопидор @ Apr 23 2009, 16:51)  А если он не вставляет содержимое системного файла в наш исходник, то почему компилятор не ругается "undefined variable" если мы юзаем переменные из системного файла? А тогда зачем вообще писать, к примеру, #include <iostream> если препроцессор всё равно не подставляет код из этого библиотечного файла в наш исходник? В h-файлах обычно определяются константы, макросы, предварительные объявления функций и ссылки на переменные. То есть, если вы используете в тексте переменные или функции из других модулей, то они должны быть объявлены до использования. Переменные - как extern, функции - как предварительное описание. Например, встретив в тексте описание viod SomeFunc(); компилятор будет спокойно воспринимать вызовы этой функции, подразумевая, что она более подробно описана в другом месте (в другом модуле, библиотеке, а может быть, в текущем, но ниже)
--------------------
Программирование делится на системное и бессистемное. ©Моё :) — а для кого-то БГ — это Bill Gilbert =)
|
|
|
|
Guest_Скопидор_*
|
Apr 23 2009, 15:18
|
Guests

|
Цитата(MrYuran @ Apr 23 2009, 19:09)  В h-файлах обычно определяются константы, макросы, предварительные объявления функций и ссылки на переменные. Да какая разница что там описано в этих h-файлах (а, кстати, где Вы увидели h в приведённой мной выше строке #include <iostream> ?) если Вы сами же пишите:Цитата(MrYuran @ Apr 23 2009, 16:27)  Код из библиотек не подставляется при компиляции, а линкуется при конечной сборке. Из чего следует, что содержимое этих "h-файлов"не добавляется препроцессором в наш исходник
Сообщение отредактировал Скопидор - Apr 23 2009, 15:23
|
|
|
|
|
Apr 23 2009, 15:38
|
Профессионал
    
Группа: Свой
Сообщений: 1 481
Регистрация: 10-04-05
Пользователь №: 4 007

|
Все что имеется в h-файлах и не отключается командами препроцессора типа #if, #ifdef включается в исходник и далее компилируется. Что вам в этом процессе не понятно? Вам надо разобраться с книгой в руках, что такое объявление переменных, функций, классов, и что такое их определение. Например, здесь можно почитатъ : http://it-library.org/articles/?c=6&&a=139. Каша у вас в голове на сегодняшний день. "Любите книгу - источник знаний"
|
|
|
|
|
Apr 23 2009, 16:57
|

Беспросветный оптимист
     
Группа: Свой
Сообщений: 4 640
Регистрация: 26-12-07
Из: Н.Новгород
Пользователь №: 33 646

|
Цитата(Скопидор @ Apr 23 2009, 19:18)  Из чего следует, что содержимое этих "h-файлов"не добавляется препроцессором в наш исходник содержимое "этих h-файлов" используется компилятором для формирования ссылок на внешние переменные и функции, которые затем цепляются линкером. При этом в объектный код компилируемого модуля никакой дополнительный код из внешних модулей не вставляется. Короче, учите матчасть. Лучше всего взять конкретный исходник (желательно грамотно написанный) и разобрать его по косточкам.
--------------------
Программирование делится на системное и бессистемное. ©Моё :) — а для кого-то БГ — это Bill Gilbert =)
|
|
|
|
Guest_Скопидор_*
|
Apr 23 2009, 17:36
|
Guests

|
Цитата(sergeeff @ Apr 23 2009, 19:38)  Вам надо разобраться с книгой в руках.... Каша у вас в голове на сегодняшний день. "Любите книгу - источник знаний" Цитата(MrYuran @ Apr 23 2009, 20:57)  Короче, учите матчасть. "P.S. Модераторы и гуру, вы реально помогайте людям кто вообще не в теме, ведб вы когда-то тоже были лохами в программинге, и вас когда-то тоже пинали, мол зелень читай больше книжки. Ведь неприятно? Люди не просят книг, а просят реальной помощи"©-Цитата(Denis89 @ Apr 10 2009, 23:56) //////////////////////////////////////////// Цитата(sergeeff @ Apr 23 2009, 19:38)  Все что имеется в h-файлах и не отключается командами препроцессора типа #if, #ifdef включается в исходник и далее компилируется. Что вам в этом процессе не понятно? Непонятно вот это:Цитата(MrYuran @ Apr 23 2009, 16:27)  Код из библиотек не подставляется при компиляции, а линкуется при конечной сборке.
Сообщение отредактировал Скопидор - Apr 23 2009, 17:38
|
|
|
|
Guest_Скопидор_*
|
Apr 23 2009, 18:31
|
Guests

|
Цитата(SysRq @ Apr 23 2009, 21:42)  Скопидор, уймитесь с форматированием. Весеннее обостение что ли?! Да блин, достало. Вместо того, чтобы конкретно разъяснить начинают отвечать в стиле "RTFM" или "учи матчасть". Говорите не интересно стало? Но я же даже в названии темы написал, что вопросы от ламера. Вот и пришлось это напомнить а также то, что и отвечающие когда-то тоже были ламерами. P.S. А зря не хотите ответы. Ваши ответы мне нравились больше всего своей конкретностью, что всё "фтему". Ну не хотите и не надо. Просто не понимаю, почему если человек знает ответ на вопрос почему бы и не ответить? Из-за вредности?
Причина редактирования: Нарушение п.3.3 и 3.4 Правил форума.
|
|
|
|
|
Apr 23 2009, 18:46
|
дятел
    
Группа: Свой
Сообщений: 1 681
Регистрация: 13-05-06
Из: Питер
Пользователь №: 17 065

|
Цитата(Скопидор @ Apr 23 2009, 22:31)  Да блин, достало. Вместо того, чтобы конкретно разъяснить начинают отвечать в стиле "RTFM" или "учи матчасть". Говорите не интересно стало? Но я же даже в названии темы написал, что вопросы от ламера. Вот и пришлось это напомнить а также то, что и отвечающие когда-то тоже были ламерами.
P.S. А зря не хотите ответы. Ваши ответы мне нравились больше всего своей конкретностью, что всё "фтему". Ну не хотите и не надо. Просто не понимаю, почему если человек знает ответ на вопрос почему бы и не ответить? Из-за вредности? up Патаму-чта Вы в самом начале сказали что ответов в книжках не нашли, но все остальные то нашли... По раздельной компиляции, все С(С++) файлы(исходники) собираются отдельно, #include "..." #include <...> обычно означает включить объявления а не определения переменных и функций (исключения конечно есть, но пока это не Ваш случай) если Вы включаете по include просто С код, то тогда это просто разбиение кода на несколько файлов, это дурной тон, но иногда делают и так... .h(.hpp) файлы библиотек(iostream например) для того и нужны чтоб правильно прилинковать библиотеки и указать на глобальныее переменные/вызовы функций которые там реализованны. Так что раздельная компиляция это совсем не миф...  более того, это просто СТАНДАРТ.
|
|
|
|
|
Apr 23 2009, 18:57
|
Частый гость
 
Группа: Свой
Сообщений: 96
Регистрация: 16-11-05
Из: г.Екатеринбург
Пользователь №: 10 930

|
Цитата(Скопидор @ Apr 24 2009, 00:31)  Непонятно вот это:
Цитата(MrYuran @ Apr 23 2009, 16:27) Код из библиотек не подставляется при компиляции, а линкуется при конечной сборке. А что не понятно? Код в библиотеке уже откомпилирован, т.е. он уже "готовый" (переведён в коды, понятные процессору). Поэтому он линкуется, т.е. присоединяется где надо при сборке.
|
|
|
|
|
Apr 23 2009, 19:02
|
Профессионал
    
Группа: Свой
Сообщений: 1 481
Регистрация: 10-04-05
Пользователь №: 4 007

|
Цитата(Скопидор @ Apr 23 2009, 21:31)  Да блин, достало. Вместо того, чтобы конкретно разъяснить начинают отвечать в стиле "RTFM" или "учи матчасть". Говорите не интересно стало? Но я же даже в названии темы написал, что вопросы от ламера. Вот и пришлось это напомнить а также то, что и отвечающие когда-то тоже были ламерами.
P.S. А зря не хотите ответы. Ваши ответы мне нравились больше всего своей конкретностью, что всё "фтему". Ну не хотите и не надо. Просто не понимаю, почему если человек знает ответ на вопрос почему бы и не ответить? Из-за вредности? По-моему десять человек вам уже разъясняли, что к чему. Пояснения уже пошли по второму кругу. Вы внятно скажите, что не понятно. А то вопли молодежи "Не понятно!!!!!!" слегка начинают доставать своей нагловатостью.
|
|
|
|
Guest_Скопидор_*
|
Apr 23 2009, 19:34
|
Guests

|
Цитата(singlskv @ Apr 23 2009, 22:46)  Патаму-чта Вы в самом начале сказали что ответов в книжках не нашли… Да не нашёл. Пока не нашёл. Не исключаю, что плохо искал. Также не исключаю, что могу найти ответы на все свои вопросы в книжках. Но сколько время на это уйдёт? Ведь не секрет, что хороший наставник сможет научить человека тому, что знает гораздо быстрей, чем если человек будет осваивать это самостоятельно идя методом проб и ошибок. Цитата(singlskv @ Apr 23 2009, 22:46)  … но все остальные то нашли... Ещё не факт, что именно в книжках. Возможно, спросили у коллег в реале или на каком-нибудь форуме. Повторяю, я ламер в C++, поэтому мои вопросы кому-то кажутся глупыми и раздражают. Я скажу этим товарищам: вспомните, что и вы когда-то были полным лузером и не осуждайте.
|
|
|
|
Guest_Скопидор_*
|
Apr 23 2009, 19:43
|
Guests

|
Цитата(singlskv @ Apr 23 2009, 22:46)  По раздельной компиляции, все С(С++) файлы(исходники) собираются отдельно Собираются в смысле компилируются (“Build”)? А где описываются «задание» компилятору, т.е. перечень CPP-файлов, подлежащих компиляции? В Makefile?
|
|
|
|
|
Apr 23 2009, 19:48
|
дятел
    
Группа: Свой
Сообщений: 1 681
Регистрация: 13-05-06
Из: Питер
Пользователь №: 17 065

|
Цитата(Скопидор @ Apr 23 2009, 23:34)  Ещё не факт, что именно в книжках. Возможно, спросили у коллег в реале или на каком-нибудь форуме.
Повторяю, я ламер в C++, поэтому мои вопросы кому-то кажутся глупыми и раздражают. Я скажу этим товарищам: вспомните, что и вы когда-то были полным лузером и не осуждайте. Раздражение здесь может быть только от одного, многим видно, что Вы не сделали и десятой доли усилий, чтоб это познать самому без посторонней помощи... Сделайте усилие над собой, а потом задавайте вопросы... и тогда Вам с удовольствием помогут.
|
|
|
|
|
Apr 23 2009, 19:52
|

Чайник, 1 литр
   
Группа: Свой
Сообщений: 655
Регистрация: 17-05-06
Из: Moscow
Пользователь №: 17 168

|
Стоило остановиться еще там: Цитата(Скопидор @ Apr 15 2009, 11:47)  В 2 этапа: сначала по отдельности компилируем все файлы (получаем OBJ-файлы), потом линкуем. Правильно? Ну компилируем, линкуем, да. Как именно выполняется компиляция, линкование; что скрыто за этими терминами; результаты работы компилятора; результаты работы линкера? Книги типа учебника по C++ для первого курса универа Т.А. Павловской с задорным страусом на обложке ессно вам ответов на эти вопросы не дадут! Берите литературу серьёзнее, раз вас интересует как оно изнутри устроено. Это даже вне C\C++ как языка. Это общий подход в языках выского уровня. PS: вы ж разбираться не стали, но громко предлагаете синими буквами сомнительных наклонностей потрындеть о ваших догадках по этому вопросу; чего ж вы хотели кроме RTFM в ответ?..
|
|
|
|
Guest_Скопидор_*
|
Apr 23 2009, 20:07
|
Guests

|
Цитата(singlskv @ Apr 23 2009, 22:46)  #include "..." #include <...> обычно означает включить объявления а не определения переменных и функций (исключения конечно есть, но пока это не Ваш случай) если Вы включаете по include просто С код, то тогда это просто разбиение кода на несколько файлов, это дурной тон, но иногда делают и так... .h(.hpp) файлы библиотек(iostream например) для того и нужны чтоб правильно прилинковать библиотеки и указать на глобальныее переменные/вызовы функций которые там реализованны. Так что раздельная компиляция это совсем не миф...  более того, это просто СТАНДАРТ. Т.е. короче говоря, в библиотечных файлах (типа iostream) ВСЕГДА находятся только объявления (не определения) типов, переменных и т.п. и прототипы функций. Когда препроцессор, просматривая исходник, «утыкается» в директиву #include <iostream>, то он ВСЕГДА вставляет содержимое РЕАЛЬНО СУЩЕСТВУЮЩЕГО (в системной директории компилятора) файла iostream, содержащего только объявления, в исходник юзверя. Затем компилятор преобразует полученный после работы препроцессора файл в объектный модуль (формат ELF или COFF). При этом в этом файле сохраняются ссылки на объекты (т.е. переменные, типы и т.п.), определённые в других файлах. Затем компилятор преобразует в объектный код все остальные CPP-файлы проекта. После этого линкер, анализируя объектный файл, полученный после компиляции PRIMARY CPP-файла (т.е. файла содержащего main) «прилепливает» к нему код из объектных файлов системных библиотек и объектных файлов, полученных после компиляции всех других CPP-файлов, и получает исполняемый файл (экзешник для DOS и Win). При этом это ЛИНКЕР определяет какой код из системных библиотек «прилеплять», а какие не надо. Я правильно понимаю?
|
|
|
|
|
Apr 23 2009, 20:17
|
Профессионал
    
Группа: Свой
Сообщений: 1 481
Регистрация: 10-04-05
Пользователь №: 4 007

|
Цитата(Скопидор @ Apr 23 2009, 23:07)  Я правильно понимаю? Почти правильно. Так оно и было, лет этак 30 тому назад. Сейчас этот процесс несколько усложнился тем, что include-файлы теперь включают : 1. inline функции, которые могут вызываться как функции, а может компилятор их текст включить в код вызывающей функции. 2. template шаблоны. Но в общем процесс сборки программы вы уловили правильно.
|
|
|
|
Guest_Скопидор_*
|
Apr 23 2009, 20:26
|
Guests

|
Цитата(singlskv @ Apr 23 2009, 23:48)  Раздражение здесь может быть только от одного, многим видно, что Вы не сделали и десятой доли усилий, чтоб это познать самому без посторонней помощи... Сделайте усилие над собой, а потом задавайте вопросы... и тогда Вам с удовольствием помогут. Вы телепат? Ну если 2 книги по C++, заученные чуть ли не наизусть - это по-Вашему не усилия, тогда я действительно не приложил НИКАКИХ усилий. Просто у меня мало свободного времени читать книги десятками томов. Вот и хотелось чтоб на каждый конкетный (может и глупый, как кажется некоторым с позиции их опыта) вопрос, такой же конкретный, и главное ОБОСНОВАННЫЙ ответ. Я думал, что если человек что-то хорошо понимает, в чём-то хорошо разбирается, то ему не будет трудно это объяснить человеку, который пока это не понимает, но хочет понять Цитата(singlskv @ Apr 24 2009, 00:13)  ...где-то так, более подробно можно обсуждать только после подробного изучения Вами соответствующей документации... О какой документации идёт речь? В книгах, которые я читал, идеология раздельной компиляции и принципы «дробления» текста программного проекта по файлам, процесс раздельной компиляции и линковки программы описаны очень поверхностно, «в двух словах».
|
|
|
|
|
Apr 24 2009, 04:24
|

Беспросветный оптимист
     
Группа: Свой
Сообщений: 4 640
Регистрация: 26-12-07
Из: Н.Новгород
Пользователь №: 33 646

|
Цитата(Скопидор @ Apr 24 2009, 00:07)  Т.е. короче говоря, в библиотечных файлах (типа iostream) ...
Я правильно понимаю? В целом да, за исключением одной неточности: библиотечные файлы (lib) содержат специально упакованный объектный код. То, что вы подключаете инклудом - это не библиотечные, а заголовочные файлы, вот они и содержат всё что вы написали. А код из библиотек подставляется на этапе линковки. В заголовочных файлах С++ (hpp) могут содержаться описания классов, и это вроде как код, но на самом деле этот код виртуальный, а "материализуется" он в том месте, где вы объявляете экземпляр класса. Вообще вместо разных умных (и глупых) книжек советую попробовать слепить какой-нибудь хелловорд в GCC, причём без разных навороченных оболочек. Просветление наступает очень быстро. Кстати, будете смеяться, но большинство гуёвых прогеров, которые пользуются разными визуальными примочками типа дельфи-билдера, никогда не видели функцию main() Некоторые даже не подозревают, что она всё-таки существует
--------------------
Программирование делится на системное и бессистемное. ©Моё :) — а для кого-то БГ — это Bill Gilbert =)
|
|
|
|
Guest_Скопидор_*
|
Apr 24 2009, 07:31
|
Guests

|
Цитата(sergeeff @ Apr 24 2009, 01:33)  И в результате всей совместной деятельности форумчан и напряжения вашей головы, процесс сборки программы стал более понятен? Да. И наверное не только мне, а всем прочим ламерам в C++, которые тоже только начинают изучение C++ и приходят на этот форум P.S.Но смею Вас заверить, что достигнув некоторого уровня понимания процесса получения исполняемого файла из нескольких библиотечных и нескольких файлов юзверя, мои ламерские вопросы не закончатся  Так что готовьтесь.  Тем более что на вопросы, которые я писал выше ответов так и не последовало (вопросы про enum, допустимые символы в строковом литерале и функцию main) Цитата(MrYuran @ Apr 24 2009, 08:24)  Вообще вместо разных умных (и глупых) книжек советую попробовать слепить какой-нибудь хелловорд в GCC, причём без разных навороченных оболочек. Просветление наступает очень быстро. Да фазу «Хелло ворлда» я прошёл уже месяца 3 назад. После чего стал «копать глубже». А потом, я не понимаю, как, написав «Хелло ворлд», и получив исполняемый файл нажатием одной единственной кнопочки «Rebuild All» я пойму как оно там всё «в кишках» компилятора происходит? От меня же это всё скрыто. Я вижу только одну кнопочку. Цитата(MrYuran @ Apr 24 2009, 08:24)  Кстати, будете смеяться, но большинство гуёвых прогеров, которые пользуются разными визуальными примочками типа дельфи-билдера, никогда не видели функцию main() Некоторые даже не подозревают, что она всё-таки существует Точно также как я не подозревал (до того как начал "копать") как происходит процесс создания исполняемого файла когда работал только с кнопкой "Rebuild All"  И на вопрос «как происходит получение исполняемого файла» я совершенно искренне ответил бы «по нажатии кнопки 'Rebuild All'» ////////////////////////////////// Цитата(MrYuran @ Apr 24 2009, 08:24)  В целом да, за исключением одной неточности: библиотечные файлы (lib) содержат специально упакованный объектный код. И формат этого lib-файла отличается от формата объектника, получаемого после компиляции PRIMARY-файла (т.е. файла, содержащего main)? А юзверь может дополнить системную библиотеку своими lib-файлами? А «подправить» lib-файл коммерческого компилятора (типа Microsoft Visual C++) у юзверя есть возможноть? //////////////////////////////////////// Цитата(MrYuran @ Apr 24 2009, 08:24)  А код из библиотек подставляется на этапе линковки. А как линкер узнаёт, какой код из объектников системных файлов нужно «пришить» к объектнику Primary-файла? Путём анализа содержимого объектника Primary-файла? А отличается ли формат объектного файла Primary-файла от формата объектных файлов других CPP-файлов, входящих в проект? А где можно почитать про формат объектных файлов (как системных {т.е. lib}, так и юзверя)?
Сообщение отредактировал Скопидор - Apr 24 2009, 07:19
|
|
|
|
Guest_Скопидор_*
|
Apr 24 2009, 09:03
|
Guests

|
Цитата(mdmitry @ Apr 24 2009, 12:09)  Вы так и не озвучили, какие книги использовали  Книги по C++
|
|
|
|
Guest_Скопидор_*
|
Apr 24 2009, 09:17
|
Guests

|
Цитата(andrew_b @ Apr 24 2009, 13:08)  Не тролльте. Вы тоже.
|
|
|
|
Guest_Скопидор_*
|
Apr 24 2009, 09:44
|
Guests

|
Цитата(mdmitry @ Apr 24 2009, 13:34)  участвовать в дальнейшем обсуждение для себя не считаю уместным. "Хозяин - Барин"© Цитата(mdmitry @ Apr 24 2009, 13:34)  На конкретный вопрос принято отвечать конкретно А я разве не конкретно ответил? P.S. А мне что некоторые как отвечали, когда я просил КОНКРЕТНЫХ ответов? А? Отвечали в стиле "RTFM", "Учи матчасть", "у тебя в голове - каша", "Читай книги" (как будто я их не читаю)
Сообщение отредактировал Скопидор - Apr 24 2009, 09:52
|
|
|
|
Guest_Скопидор_*
|
Apr 24 2009, 11:51
|
Guests

|
Цитата(Скопидор @ Apr 15 2009, 02:13)  5.Если main – функция, то можно ли её рекурсивно вызвать внутри её самой? Можно. Новички в C++!!! Кому надо привожу пример: CODE // Рекурсивные вызовы функции main из функции main // Реально достигнутый максимальный уровень вложенности main равен 12302 // Компилятор: Microsoft Visual C++ версии 6.0 // ОС: Windows XP SP2 // main.cpp // 15:05 24 апреля 2009 г. // #include <iostream> using namespace std;
int i = 0; const int Level_max = 12302; // Больше значение установить нельзя !!!
void main () { if (i <= Level_max ) { cout << "i = " << i << '\n'; // Выводим на экран значение счётчика уровня вложенности i++; // Увеличиваем счётчик уровня вложенности main (); // Вызываем рекурсивно main из main } }
// Получили на экране:
/* i = 0 i = 1 i = 2 i = 3 i = 4 i = 5 i = 6 ......... i = 12296 i = 12297 i = 12298 i = 12299 i = 12300 i = 12301 i = 12302 i = Press any key to continue */
Причина редактирования: Уменьшение видимого размера цитаты исходника.
|
|
|
|
|
Apr 24 2009, 13:48
|

Чайник, 1 литр
   
Группа: Свой
Сообщений: 655
Регистрация: 17-05-06
Из: Moscow
Пользователь №: 17 168

|
Новички C++!!! Это очень понятный язык! Кому надо привожу пример вычисления числа Пи (чем больше круг, тем точнее вычисляется): Код #define _ F-->00 || F-OO--; long F=00,OO=00; void F_OO() { _-_-_-_ _-_-_-_-_-_-_-_-_ _-_-_-_-_-_-_-_-_-_-_-_ _-_-_-_-_-_-_-_-_-_-_-_-_-_ _-_-_-_-_-_-_-_-_-_-_-_-_-_-_ _-_-_-_-_-_-_-_-_-_-_-_-_-_-_ _-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_ _-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_ _-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_ _-_-_-_-_-_-_-_-_-_-_-_-_-_-_-_ _-_-_-_-_-_-_-_-_-_-_-_-_-_-_ _-_-_-_-_-_-_-_-_-_-_-_-_-_-_ _-_-_-_-_-_-_-_-_-_-_-_-_-_ _-_-_-_-_-_-_-_-_-_-_-_ _-_-_-_-_-_-_-_-_ _-_-_-_ } int main(){F_OO();printf("%1.3f\n", 4.*-F/OO/OO);} (Извините, не мог не запостить...)
|
|
|
|
Guest_Скопидор_*
|
Apr 24 2009, 14:16
|
Guests

|
Цитата(SysRq @ Apr 24 2009, 17:48)  Новички C++!!! Это очень понятный язык! «Если язык хорошо знаком программистам, они работают более производительно. Данные, полученные при помощи модели оценки Сосото II, показывают, что про- программисты, использующие язык, с которым они работали три года или более, при- примерно на 30% более продуктивны, чем программисты, обладающие аналогичным опытом, но для которых язык является новым» © (Boehm et al., 2000). Т.е. те, кого зачастую презрительно называют новичками, ламерами и т.п. всего лишь на 30% менее эффективны, чем профи. /////////////////////////////////////////// «Если вы работаете на конкурентном рынке ПО, половина ваших знаний устареет за три года. Без обучения вы превратитесь в ископаемое.» …. «Если программист не изучил С за год или два, еще три года не сыграют особой роли» © Макконэл «Совершенный код» /////////////////////////////////////////// Модератор. Вы нарушаете п.3.1 Правил форума. Либо придерживайтесь обозначенной Вами темы, либо весь топик будет перемещен в раздел Общение - Off topics.
|
|
|
|
|
Apr 24 2009, 16:09
|
Профессионал
    
Группа: Свой
Сообщений: 1 481
Регистрация: 10-04-05
Пользователь №: 4 007

|
Цитата(Скопидор @ Apr 24 2009, 17:16)  «Если язык хорошо знаком программистам, они работают более производительно. Господа-товарищи, делающие всяческие подобные "научные" исследования просто поражают глубиной мысли. Слону понятно, что опытный работник работает более производительно, чем неопытный. Про 30% - вообще полная фигня. Код можно написать и даже запустить, но еще останется куча вопросов по его надежности, стабильности, отсутствию не очевидных ошибок периода выполнения и прочее. Какими процентами это можно подсчитать? Я никак не могу в толк взять. Вы задаете вопросы про одно. Потом перескакиваете на всякие enum и рекурсивные вызовы main. Это вопросы из спортивного интереса или на работе делать нечего? Изучение лучше всего происходит при решении конкретных "живых" задач. Вопрос про enum - это обычное приведение типов: int --> enum. Никто не запрещает это делать, но умные книги, которых вы уже ужас как много прочитали, все пишут про аккуратность приведения типов, чего и вам желаю использовать с оглядкой в будущей работе. Приколистский тон ваших сообщений не будет способствовать получению вами полезных советов от знающих людей. Хороших выходных.
|
|
|
|
Guest_Скопидор_*
|
Apr 24 2009, 19:02
|
Guests

|
Цитата(sergeeff @ Apr 24 2009, 20:09)  Я никак не могу в толк взять. Вы задаете вопросы про одно. Потом перескакиваете на всякие enum и рекурсивные вызовы main. Это вопросы из спортивного интереса или на работе делать нечего? Мне как раз есть делать что. Потому что мне нужно за неделю поднять свой уровень настолько, чтобы устроиться кодером C++. Поэтому я не тормоз, чтоб муссировать один и тот же вопрос неделями. У меня в голове крутиться одновременно тысячи вопросов, которые ищут ответа. И то, что я здесь задаю и что мне не понятно не составляет и сотой части того, что меня интересует. Я понятно объяснил?
|
|
|
|
Guest_Скопидор_*
|
Apr 24 2009, 22:13
|
Guests

|
Цитата(sergeeff @ Apr 25 2009, 01:51)  Понятно, хочется себя любимого втюхать кому-то как специалиста по С++. Успехов! Уточняю: как НАЧИНАЮЩЕГО специалиста по C++ (блин на работу уже 2 месяца не могу устроится, а 4 моих детей кушать просят). Но и реально знать C++ тоже хочу (ибо очень люблю процесс коддинга). P.S. А что? По-Вашему нужно "тормозить" и муссировать один вопрос неделями? Ведь тема называется "Вопрос ы ...", а не "Вопрос..."
|
|
|
|
|
Apr 24 2009, 22:24
|

Чайник, 1 литр
   
Группа: Свой
Сообщений: 655
Регистрация: 17-05-06
Из: Moscow
Пользователь №: 17 168

|
Раз все выяснилось, предлагаю принять правила игры: конструктивно, вопрос-ответ, без синих букв, художеств, бессмысленных цитат. Правильная игра, полагаю, будет приветствована: в тривиальных вопросах может быть скрыто нетривиальное, -- и это интересно :)
|
|
|
|
Guest_Скопидор_*
|
Apr 24 2009, 23:32
|
Guests

|
Цитата(SysRq @ Apr 25 2009, 02:24)  Раз все выяснилось, предлагаю принять правила игры: конструктивно, вопрос-ответ, без синих букв, художеств, бессмысленных цитат. Правильная игра, полагаю, будет приветствована: в тривиальных вопросах может быть скрыто нетривиальное, -- и это интересно  Вот и договорились. Это уже конструктив пошёл. //////////////////////////////////////////// Вопрос №200904250332 Почему мы пишем в проге на C++ Код cout << "Hello, World!!!" << '\n' и при выполнении программы курсор переиещается на следующую строку + переводится в начало строкиНо ведь служебный символ '\n' это символ 'Line feed', т.е. просто перевод на другую строку, без перемещения курсора в начало строкиДля перемещения строки в начало строки служит служебный символ '\r' ('Carriage return'). Т.е. по идее нужно было бы написать '\r\n'. Тогда почему в строках C++ символ '\n' работает также как '\r\n'?
|
|
|
|
|
Apr 25 2009, 00:07
|

Чайник, 1 литр
   
Группа: Свой
Сообщений: 655
Регистрация: 17-05-06
Из: Moscow
Пользователь №: 17 168

|
Цитата(Скопидор @ Apr 25 2009, 03:32)  Тогда почему в строках C++ символ '\n' работает также как '\r\n'? Исторически так уж сложилось, что в Windows корректный переход на след. строку - это \r\n (CR + LF). Поэтому \n неявно дополняется до \r\n в текстовом режиме. В std определена константа endl, пользуйтесь вместо явного '\n'. При записи в файл бинарных данных, не забывайте указывать что файл бинарный (там где это возможно, напр. fopen("file", "w b")), иначе оно тоже дополнит..
|
|
|
|
Guest_Andy Nikiforovv_*
|
Apr 27 2009, 19:14
|
Guests

|
Кто удаляет из исходника камменты (перед компиляцией) и склеивает строки разделённые символом склейки (\)? Компилятор или препроцессор? И где почитать инфу по «расколбасу» исходника прежде чем он достаётся собственно компилятору? Относительно main. Правда ли, что допустимы только две формы main: int main ( int narg, char **arg) и void main (void) ? Почему не меняется размер экзешника при последовательном заремливании строк снизу вверх? Код #include <iostream> using namespace std;
void main () { cout << "Hello, World" << endl; // 528 442 Байт Причём ENDL не катит (т.е. регистрочувствительный идентификатор) cout << "Hello, Moskau" << endl; // 528 442 Байт cout << "Hello, Moskau2" << '\n'; // 528 442 Байт cout << "Hello, Moskau3" << "\r\n"; // 528 442 Байт '\r\n' не работает; А "\r\n" работает также как '\n' и endl cout << "Hello, Moskau4" << endl; // 528 442 Байт
Сообщение отредактировал Andy Nikiforovv - Apr 27 2009, 19:07
|
|
|
|
Guest_Andy Nikiforovv_*
|
Apr 27 2009, 20:14
|
Guests

|
Написано, что параметры командной строки для Borland C++ 3.1 должны разделяться пробелами. А как быть если в параметре есть пробел? Дайте определения (в контексте языков программирования) терминов "лексика", "синтаксис", "семантика" и "грамматика". Я заметил, что некоторые ключевые слова регистронезависимы. А в книжках пишут, что в C++ все идентификаторы регистрозависимы. Объясните в чем дело. Как сделать так, чтобы под константу (const) не выделялась память? Почему сделано так, что литералу 40000 компилятор приписывает тип LONG, а не unsigned int? Функция (операция?) ЗайзэАф (sizeof) считает размер переменной/ константы с учётом выравнивания на границу слова или без учёта оного? Цитата(Andy Nikiforovv @ Apr 27 2009, 23:14)  Код #include <iostream> using namespace std;
void main () { cout << "Hello, World" << endl; // 528 442 Байт Причём ENDL не катит (т.е. регистрочувствительный идентификатор) cout << "Hello, Moskau" << endl; // 528 442 Байт cout << "Hello, Moskau2" << '\n'; // 528 442 Байт cout << "Hello, Moskau3" << "\r\n"; // 528 442 Байт '\r\n' не работает; А "\r\n" работает также как '\n' и endl cout << "Hello, Moskau4" << endl; // 528 442 Байт Почему в этом исходнике "дофени" что писать: '\n' или "\r\n"? Результат один и тот же Я написал (в консольном приложении) cout << '\a' а звука всё равно я не услышал. В чём фишка? char i ; имеет диапозон 0...255? Т.е. без знака? в отличии от int, которое по умолчанию со знаком? Какие операции допустимы над строками (символьными массивами) в "чистом" C++ (без библиотечных функций)? Какие преимущества использования манипулятора endl (кроме очистки буфера потока) по сравнению с использованием '\n'? Можно ли определить была ли очищена динамическая память, на которую указывает указатель или нет? Ну, типа, после delete указатель должен указывать не NILL? Или по стандарту это не гарантируется? Освобождение динамической памяти из-под массив происходит по команде delete []. А как менеджер кучи узнаёт сколько байт нужно освободить?
Сообщение отредактировал Andy Nikiforovv - Apr 27 2009, 19:50
|
|
|
|
|
Apr 27 2009, 20:48
|

Начинающий профессионал
    
Группа: Свой
Сообщений: 1 215
Регистрация: 25-10-06
Из: СПб
Пользователь №: 21 648

|
Цитата(Andy Nikiforovv @ Apr 27 2009, 23:14)  Кто удаляет из исходника камменты (перед компиляцией) и склеивает строки разделённые символом склейки (\)? Компилятор или препроцессор? И где почитать инфу по «расколбасу» исходника прежде чем он достаётся собственно компилятору? Взять препроцессор , запустить и посмотреть результат. Вопрос отпадет. Цитата(Andy Nikiforovv @ Apr 28 2009, 00:14)  Дайте определения (в контексте языков программирования) терминов "лексика", "синтаксис", "семантика" и "грамматика". Участники форума не на экзамене, чтобы допускать подобные формулировки. Цитата Почему сделано так, что литералу 40000 компилятор приписывает тип LONG, а не unsigned int? int и long для win32 одно и тоже. Цитата Можно ли определить была ли очищена динамическая память, на которую указывает указатель или нет? Ну, типа, после delete указатель должен указывать не NILL? Или по стандарту это не гарантируется? Освобождение динамической памяти из-под массив происходит по команде delete []. А как менеджер кучи узнаёт сколько байт нужно освободить? У Строуструпа это рассмотрено в соответствующем разделе. Какие книги по языку С++ Вы используете?
--------------------
Наука изощряет ум; ученье вострит память. Козьма Прутков
|
|
|
|
|
  |
2 чел. читают эту тему (гостей: 2, скрытых пользователей: 0)
Пользователей: 0
|
|
|