Страница 107 из 502
При использовании необязательных аргументов может возникнуть такое затруднение, как неоднозначность. Нечто подобное может произойти при перегрузке метода с необязательными параметрами. В некоторых случаях компилятор может оказаться не в состоянии определить, какой именно вариант метода следует вызывать, когда необязательные аргументы не заданы. В качестве примера рассмотрим два следующих варианта метода OptArgMeth().
<b>static void OptArgMeth(int alpha, int beta=10, int gamma = 20) {</b>
<b> Console.WriteLine("Это аргументы alpha, beta и gamma: " </b>
<b> + alpha + " " + beta + " " + gamma);</b>
<b>}</b>
<b>static void OptArgMeth(int alpha, double beta=10.0, double gamma =20.0) {</b>
<b> Console.WriteLine("Это аргументы alpha, beta и gamma: " </b>
<b> + alpha + " " + beta + " " + gamma);</b>
<b>}</b>
Обратите внимание на то, что единственное отличие в обоих вариантах рассматриваемого здесь метода состоит в типах параметров beta и gamma, которые оказываются необязательными. В первом варианте оба параметра относятся к типу int, а во втором — к типу double. С учетом этих вариантов перегрузки метода OptArgMeth() следующий его вызов приводит к неоднозначности.
<b>OptArgMeth(1); // Ошибка из-за неоднозначности!</b>
Этот вызов приводит к неоднозначности потому, что компилятору неизвестно, какой именно вариант данного метода использовать: тот, где параметры beta и gamma имеют тип int, или же тот, где они имеют тип double. Но самое главное, что конкретный вызов метода OptArgMeth() может привести к неоднозначности, даже если она и не присуща его перегрузке.
В связи с тем что перегрузка методов, допускающих применение необязательных аргументов, может привести к неоднозначности, очень важно принимать во внимание последствия такой перегрузки. В некоторых случаях, возможно, придется отказаться от применения необязательных аргументов, чтобы исключить неоднозначность и тем самым предотвратить использование метода непреднамеренным образом.
Для того чтобы показать на практике, насколько необязательные аргументы упрощают вызовы некоторых типов методов, рассмотрим следующий пример программы. В этой программе объявляется метод Display(), выводящий на экран символьную строку полностью или частично.
<b>// Использовать необязательный аргумент, чтобы упростить вызов метода.</b>
<b>using System;</b>
<b>class UseOptArgs {</b>
<b>// Вывести на экран символьную строку полностью или частично. </b>
<b> static void Display(string str, int start = 0, int stop = -1) {</b>
<b> if(stop < 0)</b>
<b> stop = str.Length;</b>
<b> // Проверить условие выхода за заданные пределы. </b>
<b> if(stop > str.Length | start > stop | start < 0) return;</b>
<b> for (int i=start; i < stop; i++)</b>
<b> Console.Write(str[i] ) ;</b>
<b> Console.WriteLine();</b>
<b> }</b>
<b> static void Main() {</b>
<b> Display("это простой тест");</b>
<b> Display("это простой тест", 12);</b>
<b> Display("3TO простой тест", 4, 14);</b>
<b> }</b>
<b>}</b>
Выполнение этой программы дает следующий результат.
<b>это простой тест </b>
<b>тест</b>
<b>простой те</b>
Внимательно проанализируем метод Display(). Выводимая на экран символьная строка передается в первом аргументе данного метода. Это обязательный аргумент, а два других аргумента — необязательные. Они задают начальный и конечный индексы для вывода части символьной строки. Если параметру stop не передается значение, то по умолчанию он принимает значение -1, указывающее на то, что конечной точкой вывода служит конец символьной строки. Если же параметру start не передается значение, то по умолчанию он принимает значение 0. Следовательно, в отсутствие одного из необязательных аргументов символьная строка выводится на экран полностью. В противном случае она выводится на экран частично. Это означает, что если вызвать метод Display() с одним аргументом (т.е. с выводимой строкой), то символьная строка будет выведена на экран полностью. Если же вызвать метод Display() с двумя аргументами, то на экран будут выведены символы, начиная с позиции, определяемой аргументом start, и до самого конца строки. А если вызвать метод Display() с тремя аргументами, то на экран будут выведены символы из строки, начиная с позиции, определяемой аргументом start, и заканчивая позицией, определяемой аргументом stop.
Несмотря на всю простоту данного примера, он, тем не менее, демонстрирует значительное преимущество, которое дают необязательные аргументы. Это преимущество заключается в том, что при вызове метода можно указывать только те аргументы, которые требуются. А передавать явным образом устанавливаемые по умолчанию значения не нужно.