Методические указания для выполнения лабораторных работ и курсовой работы содержание

Вид материалаМетодические указания

Содержание


5Лабораторная работа № 4. Подпрограммы
Глобальные описания
Объявления функций
Определение функций
3. Варианты заданий
Подобный материал:
1   2   3   4   5   6   7   8   9   ...   12

5Лабораторная работа № 4. Подпрограммы


1. Цель работы


Целью работы является изучение форматов и особенностей подрограмм отработка приемов и навыков их использования в программах на языке «С».

2. Функции

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

В языке Си подпрограммы называются функциями. Теоретически, каждая функция должна возвращать какое-либо значение. Практически, значения, возвращаемые многими функциями, просто игнорируются. В последних реализациях и определениях языка Си, включая проект стандарта ANSI и Турбо-Си, имеется возможность определения функции типа void, который означает, что эти функции никогда не возвращают никакого значения. В языке Си функцию можно объявить и определить. При объявлении функции вся программа узнает о ее существовании и все другие функции, включая main, могут к ней обращаться. При определении функции пишется программа, составляющая тело функции.

Далее идет функция main, т.е. основная часть вашей программы.

Каждая программа на языке Си имеет функцию, называемую main. Когда программа начинает выполняться, вызывается функция main, и все выполнение продолжается из нее, когда функция main закончит выполняться, работа программы оканчивается и происходит возврат в Турбо-Си или в DOS, если программа выполнялась из операционной системы.

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

Глобальные описания

Константы, типы данных и переменные, объявленные за пределами любой функции, включая main, считаются глобальными, начиная с этого момента. Это значит, что они могут использоваться любой функцией программы, находящейся после их объявления. Если в предыдущей программе переместить определение константы INFINITY в конец программы, мы получим две ошибки компилятора, одну в функции get_ratio, другую - в put_ratio, говорящие об использовании необъявленного идентификатора.

Объявления функций

Объявлять функции в Си можно двумя способами: пользуясь "классическим" и "современным" стилями. В классическом стиле, используемом во многих учебниках и программах, объявление функции выглядит так:

type funcname();

Таким образом определяется имя функции /funcname/ и тип возвращаемого ею значения /type/. В этом определении нет никакой информации о параметрах, поэтому не может проводиться проверка ошибочности их указания.

Современный стиль использует расширение стандарта ANSI, в котором имеется конструкция, называемая "прототип функции". В таком объявлении указывается информация о параметрах:

type funcname(pinfo,pinfo,...);

где информация о параметрах pinfo может иметь следующий формат:

type или type name

Иначе говоря, для каждого параметра можно указать только его тип, а можно дать и его имя. Если функция имеет переменное число параметров, вместо последнего параметра указывается многоточие /.../.

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

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

Определение функций

Также как и при объявлении, существует два способа определения функций - классический и современный. Классический вид определения функции выглядит так:

При определении по современному методу определения параметров помещаются в скобки за именем функции:

type funcname(pinfo,pinfo,...)

В этом примере pinfo представляет собой всю возможную информацию о данном параметре, включая модификатор типа и имя параметра.

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


Тогда как в современном стиле это выглядит так:

Любые объявления /констант, типов данных, переменных/, сделанные внутри данной функции, включая main, видимы /т.е. могут использоваться/ только в пределах этой функции. Кроме того, Си не позволяет использовать вложенные функции, т.е. нельзя определять одну функцию внутри другой.

Функции в программе могут помещаться в любом порядке, они считаются глобальными для всей программы, включая функции, определенные раньше текстуально. Будьте осторожны, используя функцию до того, как она определена или объявлена: когда компилятор встречает неизвестную ему функцию, он присваивает ей тип int. Если вы используете ее потом и определяете ее, как возвращающую, скажем, char*, вы получите сообщение об ошибке. Ниже приведено несколько примеров, иллюстрирующих вышесказанное. Все эти примеры построены на основе функции, определяющей принадлежность тестируемого символа русскому алфавиту. Русские буквы имеют значения кодов ASCII в пределах от кода ASCII буквы А (обозначается как ’A’) до кода ASCII буквы я (обозначается как ’я’). По оператору return возвращается значение функции=1 (истина), если символ является русской буквой, а иначе – О (ложь).

В функции main() вводится строка символов и в ней подсчитывается число русских букв.

Первый пример. В этом примере содержание функции приводится перед функцией main(), и поэтому предварительной декларации не требуется.

#include

#include

#include

#include

#include

int rus(unsigned char ch) //заголовок функции rus

{ if(ch>’A’||ch<’z’)

return 1;

else

return 0;

}

main()

{ unsigned char _ch[80],ch1;

int count=0; int i=0;

printf(“Введите строку”);

scanf(“ %s“,_ch);

while(ch1=getchar(_ch[i]!=( unsigned char)EOF)){//если не конец //строки (EOF ) ch1 = значению текущего символа

if(rus(ch1))//если ch1 – русская буква

count++;

i++;

printf(“%d число русских букв в строке = ”,count)

}

Второй пример. Здесь содержание функции приводится после функции main(), и поэтому требуется предварительная декларация функции rus().

#include

#include

#include

#include

#include

int rus(unsigned char ch); //декларация функции rus

main()

{ unsigned char _ch[80],ch1;

int count=0; int i=0;

printf(“Введите строку”);

scanf(“ %s“,_ch);

while(ch1=getchar(_ch[i]!=( unsigned char)EOF)){//если не конец //строки (EOF ) ch1 = значению текущего символа

if(rus(ch1))//если ch1 – русская буква

count++;

i++;

printf(“%d число русских букв в строке = ”,count)

}

int rus(unsigned char ch) //заголовок функции rus

{ if(ch>’A’||ch<’z’)

return 1;

else

return 0;

}

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

#include

#include

#include

#include

#include

int rus(void); //декларация функции rus

unsigned char _ch[80];

int i=0;

main()

{ unsigned ch1;

int count=0;

printf(“Введите строку”);

scanf(“ %s“,_ch);

while(getchar(_ch[i]!=( unsigned char)EOF)){//если не конец

if(rus())//если _ch[i] – русская буква

count++;

i++;

printf(“%d число русских букв в строке = ”,count)

}

int rus(void) //заголовок функции rus

{ if(_ch[i]>’A’||_ch[i]<’z’)

return 1;

else

return 0;

}


3. Варианты заданий

В качестве основы для задания используются варианты заданий в предыдущей лабораторной работе, которые должны быть выполнены следующим образом:
  1. для каждого типа цикла должна быть составлена своя функция;
  2. массивы и номера строк или столбцов, участвующих в вычислениях должны быть определены в основной программе и затем передаваться в функции;
  3. результат вычислений должен выводиться на экран из основной программы;
  4. из функций в основную программу результат вычислений возвращается через значение функции (для первого типа цикла) и через параметр (для остальных типов циклов).