Шаг 30.
Microsoft Visual C++ 2010. Язык С/С++.
Создание и использование функций. Внешние и внутренние переменные

    На этом шаге мы рассмотрим особенности использования этих переменных.

    Функции можно создавать и без параметров, если воспользоваться внешними переменными. Внешняя переменная - это переменная, значение которой известно во всех функциях, объявленных после нее, в т. ч. и в самой функции main().

    Этот прием "беспараметризации" удобно применять тогда, когда в действительности для функции надо вводить столько параметров, что это затруднит ее понимание, или когда две функции обмениваются общими данными, не вызывая друг друга. Удобно это применять и тогдя, когда в теле функции существуют массивы, требующие инициализации. Если массив, объявленный в теле функции, требует инициализации, то каждый раз при входе в функцию эта инициализация будет происходить, что продлит время выполнения программы. Лучше объявить такой массив вне функции, но так, чтобы он был известен в этой функции и один раз был проинициализирован (т. е. массив надо объявить как внешнюю переменную по отношению к данной функции).


   Замечание. Отметим, что последнее время "хорошим тоном" в программировании является явная передача параметров в функцию. Использование этого приема позволит многократно использовать такую функцию без "вспоминания", какие же внешние переменные нужны для ее работы и какие они должны иметь значения!

    Следует сказать, что существуют и внутренние (или локальные) переменные. Это такие переменные, которые объявлены в теле какого-либо блока (if, while, for, do...while) или в теле функции. Такие переменные, как говорят, локализуются в блоке объявления, т. е. известны только в самом этом блоке и не известны за его пределами. Например, можно писать:

  for(int i=0; i<0; i++) 
    {какие-то операторы} 
  i=0;

    В этом случае первая переменная i известна только в цикле for, а в выражении i=0; это будет уже другая переменная, т. к. ей компилятор присвоит совсем другой адрес. Если внешняя переменная объявлена в некотором другом файле, подключаемом с помощью директивы препроцессора #include, то она должна быть объявлена и в той программе, которую мы составляем, но с атрибутом extern. Такая переменная может инициализироваться при объявлении только раз и в месте ее основного объявления. Например, в файле F1.h имеем: int a=5; (объявление с инициализацией). В нашей программе мы должны выполнить #include "F1.h".


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

    В этом случае в программе мы должны написать: extern int а; (но не extern int a=0;, поскольку никакое другое значение присвоить при этом "дополнительном" объявлении уже нельзя). Приведем виды программ getline(), copy() и main(), которые вместо параметров используют значения внешних переменных. Основная программа будет вычислять строку максимальной длины из введенного множества строк.

// VnPer.cpp: главный файл проекта.

#include "stdafx.h"
#include <clocale> //обязательно для функции setlocale()

#include <stdio.h>	//for getchar(),putchar(), fprintf()
#include <conio.h>	//for getch()
#include <string.h>	//for strcpy()

using namespace System;

#define eof -1	//признак конца ввода (Ctrl+z)
#define MAXLINE 1000	//длина максимально возможной строки
//внешние переменные, но объявлены в этом же программном файле 
char line[MAXLINE]; 
char save[MAXLINE]; 
int max;

//Объявление функций
//Формирование строки ввода с клавиатуры в line[]:
//возвращает длину введенной строки; 
//lim - максимальное количество символов, которое можно ввести в строку line[] 
int getline() 
{
	int c,i;
	extern char line[];
	//Использование глобальной переменной в функции: т. к. 
	//описание находится в этом же файле, то в функции такую 
	//переменную можно было бы не описывать. 
	//Но мы это сделали для общего случая.
	for(i=0; i<MAXLINE-1 && (c=getchar()) != eof && c != '\n'; i++)
		line[i]=c;
	line[i]='\0'; 
	return i;
}
//	Копирование строки в строку	
void copy()
{
	extern char line[];        
	//Писать общий extern для нескольких 
	//объявляемых переменных нельзя
	extern char save[]; 
	int i=0; 
	while((save[i]=line[i]) != '\0')
		i++;
}
 
//Основная программа: выбирает строку наибольшей длины из 
//всех вводимых с клавиатуры
int main()
{
	setlocale(LC_ALL,"Russian"); //функция setlocale() с аргументами
	                             //для корректного вывода кириллицы

	int len;        //длина текущей строки
	extern int max; //здесь будет храниться длина наибольшей
	                //из 2-х сравниваемых по длине строк
	extern char save[]; 
	max=0;
	printf("Введите строку> \n"); 
	while((len=getline()) >1) {
		//когда нажмем комбинацию клавиш <Ctrl>+<Z> или <Enter>, 
		//то длина строки станет = 1
		//за счет учета признака конца '\0'
		if(len > max)
		{
			max=len;
			copy();
		}
	}
	//когда нажмем комбинацию клавиш <Ctrl>+<Z> или <Enter> (конец ввода),
	//то getline() вьдаст единичную длину (с учетом символа '\0') и 
        //мы попадем сюда
	if(max > 0)   //была введена хоть одна строка
		printf("Максимальная строка = %s\n",save); 
	_getch();

	return 0;
}
Архив проекта можно взять здесь.

    Результат работы программы приведен на рисунке 1.


Рис.1. Результат работы приложения

    На следующем шаге мы рассмотрим область действия переменных.




Предыдущий шаг Содержание Следующий шаг