Добавил:
Upload Опубликованный материал нарушает ваши авторские права? Сообщите нам.
Вуз: Предмет: Файл:
Медведев_С++_CLI_C#_Java_J#.doc
Скачиваний:
3
Добавлен:
01.07.2025
Размер:
5 Мб
Скачать
☆

Пример 4.7.1. Использование ссылочной переменной.

// C++/CLI

#include "stdafx.h"

Void main()

{

int a=1;

int &m=a; // m - ссылочная переменная

System::Console::WriteLine ("a= {0} m= {1}", a.ToString(), m.ToString());

a++;

System::Console::WriteLine ("a= {0} m= {1}", a.ToString(), m.ToString());

m++;

System::Console::WriteLine ("a= {0} m= {1}", a.ToString(), m.ToString());

}

Результат:

a= 1 m= 1

a= 2 m= 2

a= 3 m= 3

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

Функции так же могут возвращать значение ссылочного типа.

4.8Перегрузка функций

Языки С++, C++/CLI и C# позволяют определять в программе несколько функций с одним и тем же именем. Такие функции удобны и широко применяются в объектно-ориентированном программировании, когда надо выполнить аналогичные операции над данными разных типов.

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

Пример 4.8.1. Перегруженные функции swap (int &, int &) и swap (bool &,bool &).

// C+ + /CLI

Void swap (int &a, int &b) // Целочисленные параметры

{

int c=a; a=b; b=c;

}

Void swap (bool &a, bool &b) // Булевские параметры

{

bool c=a; a=b; b=c;

}

int main(array<System::String ^> ^args)

{

int x=1, y=2;

System::Console::WriteLine ("x= " + x.ToString()+ " y= " + y.ToString());

swap(x, y);

System::Console::WriteLine ("x= " + x.ToString()+ " y= " + y.ToString());

bool m=true, n=false;

System::Console::WriteLine ("m= " + m + " n= " + n);

swap (m,n);

System::Console::WriteLine ("m= " + m + " n= " + n);

return 0;

}

Результат:

x= 1 y= 2

x= 2 y= 1

m= True n= False

m= False n= True

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

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

4.9Объявление функций и передача аргументов по умолчанию

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

Void swap (int &, int &);

Void swap (char 8t, char &);

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

Пример 4.9.1. Задание значений параметров функции по умолчанию.

// C++/CLI

#include "stdafx.h"

int sum ( int а, int b= 10, int c=15 )

{ return а + b + с; }

Void main ( )

{

System::Console::WriteLine ("sum (1, 2, 3)= " + sum (1, 2, 3));

System::Console::WriteLine ("sum (1, 2)= " + sum (1, 2));

System::Console::WriteLine ("sum (1)= " + sum (1));

//System::Console::WriteLine ("sum ()= " + sum ()); // Error: 'sum':

// function does not take 0 arguments

}

Result:

sum (l, 2, 3)= 6

sum (1, 2)= 18

sum (1)= 26

4.10Передача аргументов функций в языках C++/CLI и C#

В языке С аргументы функций передаются только rio значению. Имеются два способа передачи:

  • передаётся непосредственное значение данного;

  • передаётся значение адреса данного Указатель.

Аргументы в функцию передаются через стек. В язык С++/CLI введен новый тип данных ссылка (см. раздел 4.7), а в языке C# - модификатор ref параметра функции, которые позволяют передавать аргументы и получать возвращаемое ими значения в виде ссылки. Пример 4.10.1 иллюстрирует различные способы передачи и получения данных функциями F1(), F2() и F3(). В качестве передаваемых данных взята структура, включающая целочисленную и булевскую переменные.

Пример 4.10.1. Различные способы передачи и получения данных.

// C++/CLI

#include "stdafx.h"

// Описание структуры

struct ST

{

int x; // Открытая целочисленная переменная

bool c; // Открытая булевская переменная

};

// Описание функций

void F1 (ST st) // Передаются непосредственные значения данных

{

st.x= 3; st.c= true;

}

void F2 (ST &st) // Данные передаются через ссылки

{

st.x= 3; st.c= true;

}

void F3 (ST *pSt) // Передаются значения указателей данных

{

pSt->x= 5; pSt->c= false;

}

int main(array<System::String ^> ^args)

{

ST st1 = {1, false};

System::Console::WriteLine ("st1.x= " + (st1.x).ToString() +

" stl.c= " + st1.c);

F1(st1); // Передать данные по значению

System::Console::WriteLine ("st1.x= " + (st1.x).ToString() +

" st1.c= " + st1.c);

F2 (st1); // Передать данные по ссылке

System::Console::WriteLine ("st1.x= " + (st1.x).ToString() +

" st1.c= " + st1.c);

F3 (&st1); // Передать данные по указателю

System::Console::WriteLine ("st1.x= " + (st1.x).ToString() +

" st1.c= " + st1.c);

}

Результат:

st1.x= 1 stl.c= False

st1.x= 1 st1.c= False

st1.x= 3 st1.c= True

st1.x= 5 st1.c= False

/ / C #

using System;

struct ST

{

public int x;

public String c;

}

namespace TestCSharp

{

class Program

{

static void F1(ST st) // Передаются непосредственные значения

{

st.x= 3; st.c= "b";

}

static void F2(ref ST st) // Данные передаются через ссылку

{

st.x= 3; st.c= "b";

}

static void Main(string[] args)

{

ST st1 = new ST(); st1.x= 1; st1.c= "а";

Console.WriteLine ("st1.x= {0} st1.c= {1}", st1.x, st1.c);

F1(st1);

Console.WriteLine ("st1.x= {0} st1.c= {1}", st1.x , st1.c);

F2(ref st1);

Console.WriteLine ("st1.x= {0} st1.c= {1}", st1.x, st1.c);

}

}

}

Результат:

st1.x= 1 st1.c= а

st1.x= 1 st1.c= а

st1.x= 3 st1.c= b

C++/CLI. В языке C++/GLI функции должны быть описаны или объявлены до их использования. Поэтому в C++/CLI-nporpaммe примера 4.10.1 функции F1(), F2() и F3() описаны до главной функции main(), в которой они вызываются. Ссылочные параметры помечаются символом "&".

Из результата работы программы видно, что выполнение функции F1() не меняет значения переменных структуры stl, поскольку эти значения не передаются из тела функции через аргумент. Вызов же функции F2() с ссылочным параметром и функции F3() с параметром-указателем изменил значения переменным stl.x и stl.c - осуществилась передача значений из тела функций через аргументы по ссылке и по указателю.

C#. В языке C# все функции должны принадлежать классам. Поэтому функции и описаны в классе Program, в котором, кстати, описана и главная функция Main(). Описание функций F1() и F2() как статических (глобальных) в классе Program позволяет вызывать их непосредственно в статической функции Main(), а не через класс Program. Ссылочный параметр использует модификатор ref.

Функция F2(), имеющая ссылочный параметр, в отличие от функции F1() изменила значения переменных структуры st1.