Файл: Pobegaylo_A._C_Cplus_dlya_studenta.pdf

ВУЗ: Не указан

Категория: Не указан

Дисциплина: Не указана

Добавлен: 13.12.2020

Просмотров: 4108

Скачиваний: 28

ВНИМАНИЕ! Если данный файл нарушает Ваши авторские права, то обязательно сообщите нам.
background image

Часть I. Язык программирования С 

86 

void  f(int* const a, int n, int m) 

  int i; 
  for (i = 0; i < n * m; ++i) 
    ++a[i]; 

В этом случае используется тот факт, что элементы статических 
массивов хранятся в памяти последовательно. Вызов этой функ-
ции будет выглядеть следующим образом: 

  int a[2][2] = {1, 2, 3, 4}; 
  f(&a[0][0], 2, 2); 

6.6. Указатели на функции  
(функторы) 

Язык  программирования  C  позволяет  определять  указатели  на 
функции, которые имеют следующий вид: 

  спецификатор_типа (*имя_указателя)(список_параметров) 

Например,  указатель  на  функцию,  которая  возвращает  значение 
типа 

int

  и  имеет  два  параметра  типа 

int

,  может  быть  объявлен 

как: 

  int (*fp)(int x, int y); 

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

int add(int x, int y) { return x + y; } 

То ее адрес можно присвоить указателю 

fp

 следующим образом: 

  fp = &add; 

Учитывая,  что  имя  функции  является  адресом  этой  функции  в 
памяти,  указателю  на  функцию  можно  просто  присвоить  имя 
функции. То есть: 

  fp = add; 


background image

Глава 6. Функции 

87 

Так как указателю на функцию могут присваиваться адреса раз-
личных функций при условии совпадения типа параметров и типа 
возвращаемого  значения,  то  указатель  на  функцию  часто  назы-
вают 

функтором

Вызвать функцию через указатель можно двумя способами: 

 

(*имя_указателя)(список_аргументов); 

 

имя_указателя(список_аргументов). 

Представляется,  что  первый  способ  более  наглядный,  т. к.  явно 
указывает, что функция вызывается через указатель. 
В листинге 6.3 приведена программа, в которой функции сложе-
ния и вычитания двух чисел вызываются через указатель. 

Листинг 6.3. Вызов функций через указатель 

#include <stdio.h> 
int add(int x, int y) { return x + y; } 
int sub(int x, int y) { return x - y; } 
int main(void) 

  int (*p)(int, int); 
  p = add; 
  printf("1 + 2 = %d\n", (*p)(1, 2)); 
  p = sub; 
  printf("1 - 2 = %d\n", p(1, 2)); 
  return 0; 

Тип указателя на функцию может также использоваться как тип 
возвращаемого  функцией  значения  и  тип  параметра  функции. 
Например, в листинге 6.4 приведена функция 

foo

, которая полу-

чает  в  качестве  параметра  указатель  на  функцию  и  просто  воз-
вращает его. 

Листинг 6.4. Использование типа указателя на функцию  
как типа возвращаемого значения и типа параметра функции 

#include <stdio.h> 
int (*foo(int (*p)(int)))(int) { return p; } 


background image

Часть I. Язык программирования С 

88 

int inc(int x) { return ++x; } 
int dec(int x) { return --x; } 
int main(void) 

  int (*f) (int);    /* указатель на функцию */ 
 
  f = foo(inc);      /* устанавливаем указатель на inc */ 
  printf("2 + 1 = %d\n", (*f)(2)); 
 
  f = foo(dec);      /* устанавливаем указатель на dec */ 
  printf("2 - 1 = %d\n", (*f)(2)); 
 
  return 0; 

В  заключение  этого  раздела  отметим,  что  над  указателями  на 
функции нельзя выполнять никаких арифметических операторов. 

 


background image

  

 
 

Г Л А В А  

 
 
 

Структура программы  

на языке С 

7.1. Область видимости 
идентификатора 

Если  переменная  объявлена  вне  какого-либо  блока,  то  такая  пе-
ременная называется 

глобальной

. В противном случае переменная 

называется 

локальной

Областью  видимости  идентификатора

  называется  наибольшая 

область  программы,  в которой  можно сослаться  на  этот  иденти-
фикатор. Существуют четыре типа областей видимости: 

 

блок; 

 

функция; 

 

прототип функции; 

 

исходный файл. 

Глобальные  переменные  видимы  внутри  исходного  файла,  в  ко-
тором они определены. 
Локальные  переменные  видимы  только  внутри  блока  или  функ-
ции, в которой они определены. Локальная переменная скрывает 
любую  переменную  с  тем  же  именем,  объявленную  вне  этого  
блока. 
В  листинге  7.1  приведен  пример,  демонстрирующий  сокрытие 
имен переменных. 

  

 


background image

Часть I. Язык программирования С 

90 

Листинг 7.1. Сокрытие имен переменных 

#include  <stdio.h> 
int n = 1; 
int main(void) 

  printf("n = %d\n", n);      /* n = 1 */ 
  { 
    int n = 2; 
    printf("n = %d\n", n);    /* n = 2 */ 
    { 
      n = 3; 
      printf("n = %d\n", n);  /* n = 3 */ 
    } 
  } 
  return 0; 

Параметры функции видны только внутри функции или объявле-
ния этой функции. 
Функции всегда определяются вне какого-либо блока. Областью 
видимости  функции  является  исходный  файл,  в  котором  эта 
функция определена. 

7.2. Время существования  
переменных и функций 

Время существования переменной

 или 

функции

 определяется как 

время, в течение которого эта переменная или функция хранится 
в памяти компьютера. 
Глобальные  переменные  существуют  в  течение  всего  времени 
выполнения программы и хранятся в фиксированной области па-
мяти программы, которая задается во время ее компиляции. Если 
глобальная  переменная  не  проинициализирована, то  компилятор 
устанавливает ее значение в ноль. 
Память  для  локальных  переменных  выделяется  динамически  во 
время исполнения программы. При вызове функции или входе в 


Смотрите также файлы