Г. Шилтд - Самоучитель C++ (DJVU) (1114955), страница 13
Текст из файла (страница 13)
Гбпс!цде <аозКгеак> цз(пя пагпезрасе зес(; // Перегрузка функции апп() тремя способами // (пг 1п1)пе (пг га1п (1пс а, 1пГ Ь) ( гесыгп а < Ь 2 а: Ь; // 1опе пз1(пе 1опя ламп(1опд а, (опя Ь) Глава 2. Вве ение в классы гегигп а < Ь? а: Ь; О ((оиЫе ш1ше ао~ь1е гаш(г(оиЫе а, доцЫе ь) ( гегцгп а < Ь? а: Ь; !и( паьп () ( соц1 « ты(-10, 10) « "хп" я соц( «агп(-1с.о1, 100.002) « "~п"; сов( « жтп (-1сь, 121 ) « "хп"; гегигп 0; 1. В главе 1 вы перегружали функцию аЬвО так, чтобы она находила абсолютные значения типа 1вг, 1овя и (1овЫе.
Модифицируйте программу, чтобы эти функции стали встраиваемыми. 2. Почему следующая функция может не компилироваться как встраиваемая? чо(г( г1() 1П1 3.; 1'огс( = 0; 1 < 10; 1++) соШ «1; 2.7. Встраиваемые функции в объявлении класса Если определение функции-члена достаточно короткое, его можно включить в объявление класса. Поступив таким образом, мы заставляем, если это возможно, функцию стать встраиваемой. Если функция задается внутри объявления класса, ключевое слово 1в11ве не требуется.
(Однако использование его в такой ситуации не является ошибкой.) Например, как показано ниже, функция 4ЬЫЫео из предыдущего раздела может быть по умолчанию сделана встраиваемой: Самоучитель Сч-» 76 ()1пс1пде <аоаетеатк> цзгпц папезрасе вЫ; с1авв ваюр ( 1пс 3, рцЬ11с: затр (гпь а, ьпс Ь) !* Функция бтчгвгЫе (), которая здесь определяется, по умолчанию становится встраиваемой, тпс бгжтв5Ые () ( лесцпп !(1%3)' ) валлер:: выпр (г е а, гпс Ь) а ) л=Ь; гпс юагп () ( затр оЬ1 (10, 2), оЬ2 (10, 3); зто истина Н (оЫ бгчгагЫе() ) соле « "10 делится на 21п"; // это ложь гг (оЬ2.с)1 ттвтЬ1е () ) соцс « "10 делится на Зхп"; тститп 0; Как видите, код функции йла1ЫеО находится внутри объявления класса ватр.
Отметьте, что никакого другого определения функции ййяЫеО не нужно, это даже запрещено. Определение функции йчЫ)з1еО внутри класса яаа)р автоматически заставляет ее стать встраиваемой функцией. Если функция, заданная внутри объявления класса, не может стать встраиваемой функцией (поскольку были нарушены ограничения), она, обычно, преобразуется в обычную функцию. Отметьте, как именно функция йяяыео задается внутри класса аатр, особенно само тело функции. Оно целиком расположено на одной строке. Такой формат для программ С++ является совершенно обычным, если функция объявляется внутри объявления класса.
Такое объявление становится более компактным. Однако класс ваар мог бы быть описан и так: с1азз напр ( гпс 1, зг Глава 2. Введение в классы 77 рцЫ1с: за~ор(впав а, )пт Ь); / Функция б1~~1з1Ые (), которая здесь определяется, по умолчанию становится встраиваемой. в/ (пт с(ъч1зъЫе () гетигп 1(1ЪЗ); Здесь в определении функции Йу1з!ЫеО используется более или менее стандартный стиль отступов. С точки зрения компилятора, компактный и стандартный стили не отличаются. Однако в программах С++ при задании коротких функций внутри определения класса обычно используется компактный стиль.
На применение таких встраиваемых функций накладываются те же ограни- чения, что и на применение обычных встраиваемых функций. «.'пз-" - з -". с "" и "-.,(йРИМЕРЫ,„': 1. Вероятно наиболее традиционным использованием встраиваемых функций, определяемых внутри класса, является определение конструктора и деструктора.
Например, класс аыпр может быть определен более эффективно: гг(пс!ис(е <1озтгеал:> из)пя пагпезрасе зес(г с1азз запзр ( 1пт з. Э раас: // встраиваемый конструктор затер(ъпса, )птЬ) ( 1=а;1 =Ь; ) (п( с(ъчъз1Ые() 1 гекпгп ! (1%З); Определения функции за)прО внутри класса запьр достаточно, и никакого другого определения не требуется. 2. Иногда короткие функции могут включаться в объявление класса даже тогда, когда преимущества встраивания мало что дают или вовсе не проявляются.
Рассмотрим следующее объявление класса: с1азз тус1азз 3.пс 1; Самоучитель С+ч- рпЫ1с: тус1ааа(1пс и) ( 1 = и; чоЫ аЛси() 1 сои(. « 1; ) Здесь функция вЬоут() по умолчанию становится встраиваемой. Однако, как вы, наверное, знаете, операции ввода/вывода, по сравнению с операциями процессор/память, являются настолько медленными, что какой бы то ни было эффект от устранения вызова функции практически отсутствует. Однако в программах на С++, как правило, можно встретить такие короткие функции внутри класса.
Делается это просто для удобства, поскольку никакого вреда не приносит. 1. Переделайте класс в1ас1( из раздела 2.1, пример 1, так, чтобы в классе, где это возможно, использовались встраиваемые функции. 2. Переделайте класс в1г$уре из раздела 2.2, пример 3, так, чтобы в классе ис- пользовались встраиваемые функции. Теперь вам необходимо выполнить следующие упражнения и ответить на вопросы. 1. Что такое конструктор? Что такое деструктор? Когда они вызываются? 2.
Создайте класс Иве, который рисует на экране линию. Храните длину линии в виде закрытой целой переменной 1еп, Конструктор Иве должен иметь один параметр — длину линии. Он должен сохранять длину линии и собственно рисовать линию. Если ваша система не поддерживает графику, отобразите линию, используя символ *. Необязательное задание: Для удаления линии используйте деструктор Иве.
3. Что выведет на экран следующая программа? ((.гпс1пс(е <ьсзт.асеев> па1.пд иатиеьрасе асс(; (п( паз.п () 1и11= 10; 1с с 1 = :ОООООО; с(оиЬ1е с( = — 0.0009; Глава 2. Введение вклассы сонг«1«''«1«''«г(; сонг « "1п": гегигп О; 4. Добавьте производный класс, который наследует класс агеа с! из раздела 2.3, упражнение 1. Назовите этот класс суИп(1ег и пусть он вычисляет плошадь поверхности цилиндра. Эта площадь задается так: 2 * р) * К2 + р( " О " Н. 5. Что такое встраиваемая функция? В чем ее преимушества и недостатки? 6. Измените следующую программу так, чтобы все функции-члены по умолчанию стали встраиваемыми функциями: ((1пс1пг(е <ьозггеаа> ив(пя пагпезраса вгг(; с!азв тпус1азз (пг1, 3; ро)о11с: тус1азз(1пс х, (пГ у); чоЫ зпоы(); аус1азз::~пус1азз (1по х, (пГ у) (=х чогс( гпус1азз:."в)тои() сонг.
«1 « "" "" « ) « "1п" г 1пг ваап() ( еь с1азз соппг (2, 3)р соипс.зпои(); гегигп О; 7. В чем отличие между классом и структурой? 8. Правилен ли следующий фрагмент? ипюп ( Поаг Г; ипзудпеб 1пс Ыг.з; )' ВО Самоучитель С-н- В этом разделе проверяется, хорошо ли вы усвоили материал этой и предыдущих глав.
1. Создайте класс ргошр1. Для вывода на экран строки-приглашения включите в класс конструктор. Помимо строки-приглашения конструктор должен выполнить ввод набранного вами целого. Сохраните это значение в'закрытой переменной соввг. При удалении объекта типа ргошр1 должен быть подан звуковой сигнал, причем столько раз, сколько задано пользователем в переменной соип1, 2.
В главе 1 вы создали программу для преобразования футов в дюймы. Теперь для этой цели создайте класс. Класс должен хранить число футов и его эквивалент в дюймах. Передайте конструктору класса число футов и при этом он должен вывести на экран число дюймов. 3. Создайте класс йсе, который содержит закрытую целую переменную. Создайте функцию го11(), использующую стандартный генератор случайных чисел гапйо, для получения чисел от 1 до 6.
Функция гоПО должна вывести это значение на экран. Глава 3 Подробное изучение классов В этой главе вы продолжите изучение классов. Вы узнаете о том, как присвоить один объект другому, как объекты передаются функциям в качестве аргументов, как сделать объект возвращаемым значением функций. Вы также узнаете о новом важном типе функций: дружественных ((йепд) функциях. Перед тем как продолжить, вы должны правильно ответить на следующие вопросы и сделать упражнения.
1. Пусть дан следующий класс, каковы имена его конструктора и деструктора? стане набам'-'~ тпрр х, у; р1т1от т с нпиките конструкторы и деструкторы 2. Когда вызывается конструктор? Когда вызывается деструктор? 3. Пусть дан следующий базовый класс, покажите, как он может наследоваться производным классом Мага.
с1аве р(апета ( 1п1 тоопз; доиЫе с1Ъес ткете еып; доиЫе д 1агпе1ег; доиЫе ваез; рпь1гс; I/ . 1' 4. Имеются два способа сделать функцию встраиваемой. Что это за способы? 5. Приведите, по крайней мере, два ограничения на использование встраи- ваемых функций. Свмоучитель С++ 82 б. Пусть дан следующий класс, покажите, каким образом объявить объект оЬ, чтобы значение 100 передать переменной а, а значение Х переменной с. с1аая зал(р1е 1 тпрр. а," сЬаг с; ри)о11с: зюврге(ъпт х, сЬаг сЬ) 1 а — х; с = сп; ) // 3.1. Присваивание объектов Если тип двух объектов одинаков, то один объект можно присвоить другому. По умолчанию, когда один объект присваивается другому, делается поразрядная копия всех данных-членов копируемого объекта. Например, когда объект о1 присваивается объекту о2, то содержимое всех данных объекта о1 копируется в соответствующие члены объекта о2. Это иллюстрируется следующей программой: Пример присваивания объекта ()ъпс1пс(е «ьозтвеып> пятно патеярасе з~Ф с1аяя тус1азз тпб а, )о; ре)Ы то: уоЫ зее (тамит, тпс 1) 1 а — 1; Ь = 1; ) уоЫ зпои() 1 соШ « а « ' ' сс Ь « "1п"; 1п(.тазп ( ) ( тус1аяя о1, о2; о1.зет.(10, 4); о1 присваивается о2 о2 = о1; о1.знои(); о2 .
знои() ( песитп О; В этом примере переменным а и Ь объекта о1 присваиваются соответственно значения 10 и 4. Далее объект о1 присваивается объекту о2. Это приво- Глава 3. Подробное изучение классов дит к тому, что текущее значение переменной о1.а присваивается переменной о2.а, а текущее значение переменной о1.Ь вЂ” о2.Ь. Таким образом, в процессе выполнения программа выведет на экран следующее: 10 4 1О 4 Запомните, что присваивание двух объектов просто делает одинаковыми данные этих объектов. Два объекта остаются по-прежнему совершенно независимыми.
Например, после выполнения присваивания вызов функции- члена о1лвЦ) для задания значения о!.а не влияет ни на объект о2, ни на значение его переменной а. Е Важно понимать, что в инструкции присваивания можно использовать только объекты одинакового типа. Если тип объектов разный, то при компиляции появится сообщение об ошибке. Более того, важно не только чтобы типы объектов были физически одинаковыми, а чтобы одинаковыми были также имена типов. Например, следующая программа неправильна: О Эта программа содержит ошиаку ((ьпс1пс(е <Ьовекевл1> Пя(ня Пан(ЕяраСЕ вес(; с1азв гпус1авв Г (пт а, Ь; рпЬ11с: уоЫ вее(1п~ 1, (пт З) ( а - 1; Ь = Зг ) уоЫ впои(1 1 сопт « а « ' ' « Ь « "'~п"; ) /* Этот класс похож на класс птус!азз, но из-за другого имени класса для компилятора он считается другим типом.