Программирование >>  Инициализация объектов класса, структура 

1 ... 103 104 105 [ 106 ] 107 108 109 ... 395


правильно: возвращается список символов

Функция может возвращать типы классов, в частности контейнеры. Например:

list<char> foo bar();

(Этот подход не очень эффективен. Обсуждение тина возвращаемого значения см. в разделе 7.4.)

Тип возвращаемого функцией значения должен быть явно указан. Приведенный ниже

ошибка: пропущен тип возвращаемого значения

код вызывает ошибку компиляции:

const is equa1( vector<int> vl, vector<int> v2 );

В предыдущих версиях С++ в подобных случаях считалось, что функция возвращает значение типа int. Стандарт С++ отменил это соглашение. Правильное объявление

правильно: тип возвращаемого значения указан

is equal() выглядит так:

const bool is ea1 ( vector<int> vl, vector<int> v2 );

7.2.2. Список параметров функции

Список параметров не может быть опущен. Функция, которая не требует параметров, должна иметь пустой список либо список, состоящий из одного ключевого слова void.

int fork();

Например, следующие объявления эквивалентны:

int fork( void );

Такой список состоит из названий типов, разделенных запятыми. После имени типа может находиться имя параметра, хотя это и необязательно. В списке параметров не разрешается использовать сокращенную запись, соотнося одно имя типа с несколькими

int manip( int vl, v2 ); ошибка

параметрами:

int manip( int vl, int v2 ); правильно

правильно: указатель на перв элемент массива int *foo bar() ;

(Размер массива должен быть известен вызывающей программе.)



gcd( hello , world )

error: invalid argument types ( const char *, const char * ) --

expecting ( int, int ошибка: неверные типы аргументов ( const char *, const char * ) ожидается ( int, int )

gcd( 24312 )

error: missing value for second argument ошибка: пропущено значение второго аргумента

А если вызвать эту функцию с аргументами типа double? Должен ли этот вызов расцениваться как ошибочный?

gcd( 3.14, 6.29 );

Имена параметров не могут повторяться. Имена, фигурирующие в определении функции, можно и даже нужно использовать в ее теле. В объявлении же функции они не обязательны и служат средством документирования ее интерфейса. Например:

void print( int *array, int size );

Имена параметров в объявлении и в определении одной и той же функции не обязаны совпадать. Однако употребление разных имен может запутать пользователя.

С++ допускает сосуществование двух или более функций, имеющих одно и то же имя, но разн1е списки параметров. Такие функции наз1ваются перегруженными. О списке параметров в этом случае говорят как о сигнатуре функции, поскольку именно он используется различения разных версий одноименных функций. Имя и сигнатура однозначно идентифицируют версию. (Перегруженные функции подробно обсуждаются в главе 9.)

7.2.3. Проверка типов формальных параметров

Функция gcd() объявлена следующим образом:

int gcd( int, int );

Объявление говорит о том, что имеется два параметра типа int. Список формальных параметров предоставляет компилятору информацию, с помощью которой тот может проверить типы передаваемых функции фактических аргументов.

Что будет, если попытаться вызвать функцию gcd() с аргументами типа char*?

gcd( hello , world );

А если передать этой функции не два аргумента, а только один? Или больше двух? Что случится, если потеряется запятая между числами 24 и 312?

gcd( 24312 );

Единственное разумное поведение компилятора - сообщение об ошибке, поскольку попытка выполнить такую программу чревата весьма серьезными последствиями. С++ действительно не пропустит подобные вызовы. Текст сообщения будет выглядеть примерно так:



(a) set( int *, int );

(b) void func();

(c) string error( int );

Какие из следующих прототипов функций содержат ошибки? Объясните.

(d) arr[10] sum( int *, int );

Упражнение 7.2

Напишите прототипы для следующих функций:

Функция с именем comipare, имеющая два параметра тина ссылки на класс miatrix и возвращающая значение типа bool.

Функция с именем extract без параметров, возвращающая контейнер set для хранения значений тина int. (Контейнерный тин set описывался в разделе 6.13.)

Упражнение 7.3

double calc( double );

int count( const string &, char );

void sum( vector<int> &, int );

Имеются объявления функций:

vector<int> vec( 10 );

Какие из следующих вызовов содержат ошибки и почему?

Как было сказано в разделе 4.14, значение тина double может быть преобразовано в int. Следовательно, считать такой вызов ошибочным было бы слишком сурово. Вместо этого аргументы неявно преобразуются в int (отбрасыванием дробной части) и таким образом требования, налагаемые на типы параметров, выполняются. Поскольку при подобном преобразовании возможна потеря точности, хороший компилятор выдаст предупреждение. Вызов превращается в

gcd( 3, 6 );

что дает в результате 3.

С++ является строго типизированным языком. Компилятор проверяет аргументы на соответствие типов в каждом вызове функции. Если тип фактического аргумента не соответствует типу формального параметра, то производится попытка неявного преобразования. Если же это оказывается невозможным или число аргументов неверно, компилятор выдает сообщение об ошибке. Именно поэтому функция должна быть объявлена до того, как программа впервые обратится к ней: без объявления компилятор не обладает информацией для проверки типов.

Пропуск аргумента при вызове или передача аргумента неуказанного типа часто служили источником ошибок в языке С. Теперь такие погрешности обнаруживаются на этапе компиляции.

Упражнение 7.1



1 ... 103 104 105 [ 106 ] 107 108 109 ... 395

© 2006 - 2024 pmbk.ru. Генерация страницы: 0
При копировании материалов приветствуются ссылки.
Яндекс.Метрика