- •8 Подробнее о методах и классах
- •8.1 Управление доступом к членам класса
- •8.1.1 Модификаторы доступа
- •8.1.2 Организация закрытого и открытого доступа
- •8.1.3 Практический пример организации управления доступом
- •8.2 Передача объектов методам по ссылке
- •8.2.1 Способы передачи аргументов методу
- •8.3 Использование модификаторов параметров ref и out
- •8.3.1 Использование модификатора параметра ref
- •8.3.2 Использование модификатора параметра out
- •8.3.3 Использование модификаторов ref и out для ссылок на объекты
- •8.4 Использование переменного числа аргументов
- •8.5 Возврат объектов из методов
- •8.5.1 Возврат массива из метода
- •8.6 Перегрузка методов
- •8.7 Перегрузка конструкторов
- •8.7.1 Вызов перегружаемого конструктора с помощью ключевого
- •8.8 Инициализаторы объектов
- •8.9 Необязательные аргументы
- •8.9.1 Необязательные аргументы и перегрузка методов
- •8.9.2 Необязательные аргументы и неоднозначность
- •8.9.3 Практический пример использования необязательных аргументов
- •8.10 Именованные аргументы
- •8.11 Метод Main ()
- •8.11. 1 Возврат значений из метода Main()
- •8.11.2 Передача аргументов методу Main()
- •8.12 Рекурсия
- •8.13 Применение ключевого слова static
- •8.13.1 Статические конструкторы
- •8.14 Статические классы
8.3.2 Использование модификатора параметра out
Иногда ссылочный параметр требуется использовать для получения значения из метода, а не для передачи ему значения. Допустим, что имеется метод, выполняющий некоторую функцию, например, открытие сетевого сокета и возврат кода успешного или неудачного завершения данной операции в качестве ссылочного параметра. В этом случае методу не передается никакой информации, но в то же время он должен возвратить определенную информацию. Главная трудность при этом состоит в том, что параметр типа ref должен быть инициализирован определенным значением до вызова метода. Следовательно, чтобы воспользоваться параметром типа ref, придется задать для аргумента фиктивное значение и тем самым преодолеть данное ограничение. Правда, в С# имеется более подходящий вариант выхода из подобного затруднения воспользоваться модификатором параметра out.
Модификатор параметра out подобен модификатору ref, за одним исключением: он служит только для передачи значения за пределы метода. Поэтому переменной, используемой в качестве параметра out, не нужно (да и бесполезно) присваивать какое-то значение. Более того, в методе параметр out считается неинициализированным, т.е. предполагается, что у него отсутствует первоначальное значение. Это означает, что значение должно быть присвоено данному параметру в методе до его завершения. Следовательно, после вызова метода параметр out будет содержать некоторое значение.
Ниже приведен пример применения модификатора параметра out. В этом примере программы для разделения числа с плавающей точкой на целую и дробную части используется метод GetParts() из класса Decompose. Обратите внимание на то, как возвращается каждая часть исходного числа.
Листинг 8.9
// Использовать модификатор параметра out.
using System;
class Decompose
{
/* Разделить числовое значение с плавающей точкой
На целую и дробную части. */
public int GetParts(double n, out double frac)
{
int whole;
whole = (int) n;
frac = n-whole; //передать дробную часть числа через параметр frac
return whole; // возвратить целую часть числа
}
}
class UseOut
{
static void Main()
{
Decompose ob = new Decompose();
int i;
double f;
i = ob.GetParts(10.125, out f);
Console.WriteLine("Целая часть числа равна " + i);
Console.WriteLine("Дробная часть числа равна " + f);
}
}
Выполнение этой программы дает следующий результат.
Целая часть числа равна 10
Дробная часть числа равна 0.125
Метод GetParts() возвращает два фрагмента информации. Во-первых, целую часть исходного числового значения переменной n обычным образом с помощью оператора return. И во-вторых, дробную часть этого значения посредством параметра frac типа out. Как показывает данный пример, используя модификатор параметра out, можно организовать возврат двух значений из одного и того же метода.
Разумеется, никаких ограничений на применение параметров out в одном методе не существует. С их помощью из метода можно возвратить сколько угодно фрагментов информации. Рассмотрим пример применения двух параметров out. В этом примере программы метод HasComFactor() выполняет две функции. Во-первых, он определяет общий множитель (кроме 1) для двух целых чисел, возвращая логическое значение true, если у них имеется общий множитель, а иначе логическое значение false. И во-вторых,.он возвращает посредством параметров типа out наименьший и наибольший общий множитель двух чисел, если таковые обнаруживаются.
Листинг 8.10
// Использовать два параметра типа out.
using System;
class Num
{
/* Определить, имеется ли у числовых значений переменных x и v
общий множитель. Если имеется, то возвратить наименьший и
наибольший множители посредством параметра типа out. */
public bool HasComFactor(int x, int y,
out int least, out int greatest)
{
int i;
int max = x < y ? x : y;
bool first = true;
least = 1;
greatest = 1;
// Найти наименьший и наибольший общий множители.
for(i=2; i <= max/2 + 1; i++) {
if( ((y%i)==0) & ((x%i)==0) ) {
if(first) {
least = i;
first = false;
}
greatest = i;
}
}
if(least != 1) return true;
else return false;
}
}
class DemoOut
{
static void Main()
{
Num ob = new Num();
int lcf, gcf;
if(ob.HasComFactor(231, 105, out lcf, out gcf)) {
Console.WriteLine("Наименьший общий множитель " +
"чисел 231 и 105 равен " + lcf);
Console.WriteLine("Наибольший общий множитель " +
"чисел 231 и 105 равен " + gcf);
}
else
Console.WriteLine("Общий множитель у чисел 35 и 49 " +
" отсутствует.);
if(ob.HasComFactor(35, 51, out lcf, out gcf)) {
Console.WriteLine("Наименьший общий множитель " +
"чисел 35 и 51 равен " + lcf);
Console.WriteLine("Наибольший общий множитель " +
"чисел 35 и 51 равен " + gcf);
}
else
Console.WriteLine("Общий множитель у чисел 35 и 51 " +
" отсутствует.);
}
}
Обратите внимание на то, что значения присваиваются переменным lcf и gcf в методе Main() до вызова метода HasComFactor(). Если бы параметры метода HasComFactor() были типа ref, а не out, это привело бы к ошибке. Данный метод возвращает логическое значение true или false, в зависимости от того, имеется ли общий множитель у двух целых чисел. Если он имеется, то посредством параметров типа out возвращаются наименьший и наибольший общий множитель этих чисел. Ниже приведен результат выполнения данной программы.
Наименьший общий множитель чисел 231 и 105 равен 3
Наибольший общий множитель чисел 231 и 105 равен 21
Общий множитель у чисел 35 и 51 отсутствует.
