Когда я должен использовать параметры?

Я прошел шаги в в этом ответе и до сих пор не получил разрешение. Я продолжал искать в Интернете и обнаружил, что вы можете получить эту ошибку, если вы пытаетесь экспортировать APK, когда устройство Android подключено к компьютеру.

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

50
задан Motti 22 July 2009 в 18:44
поделиться

9 ответов

Выход хорош, если у вас есть функция TryNNN , и ясно, что выходной параметр всегда будет установлен, даже если функция не завершится успешно. Это позволяет вам полагаться на тот факт, что локальная переменная, которую вы объявляете, будет установлена, вместо того, чтобы позже в вашем коде проверять значение null. (Комментарий ниже указывает, что для параметра можно установить значение null , поэтому вы можете проверить документацию для функции, которую вы вызываете, чтобы убедиться, так ли это.) Это делает код стал немного понятнее и удобнее для чтения. Другой случай - когда вам нужно вернуть некоторые данные и статус по условию метода, например:

public bool DoSomething(int arg1, out string result);

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

Недостатком является то, что вам нужно объявить локальную переменную, чтобы использовать их:

string result;
if (DoSomething(5, out result))
    UpdateWithResult(result);

Вместо:

UpdateWithResult(DoSomething(5));

Однако это может даже не быть недостатком, это зависит от дизайна, который вы собираетесь использовать. В случае DateTime предоставляются оба средства (Parse и TryParse).

27
ответ дан 7 November 2019 в 11:08
поделиться

Ну, как и многое другое, это зависит. Давайте посмотрим на параметры

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

В случае TryParse использование параметра out является эффективным - вам не нужно создавать новый тип, который будет составлять 16 Б накладных расходов (на машинах 32 Б) или нести затраты на выполнение о том, что они собирают мусор после звонка. TryParse может быть вызван, например, из цикла - поэтому здесь правила out params.
Для функций, которые не будут вызываться внутри цикла (т. Е. Производительность не является основной проблемой), возврат одного составного объекта может быть «чище» (субъективно для наблюдателя). Теперь с анонимными типами и динамической типизацией это могло бы стать еще проще.

Примечание:

  1. out params имеют некоторые правила, которые необходимо соблюдать, т.е. компилятор будет гарантировать, что функция инициализирует значение прежде, чем он выйдет. Таким образом, TryParse должен установить для параметра out какое-то значение, даже если операция синтаксического анализа завершилась неудачно
  2. Шаблон TryXXX является хорошим примером того, когда использовать параметры out - Int32.TryParse был введен, потому что люди жаловались на перфоманс перехвата исключений, чтобы знать если синтаксический анализ не удался. Также наиболее вероятная вещь, которую вы бы сделали в случае успешного синтаксического анализа, заключается в получении проанализированного значения - использование параметра out означает, что вам не нужно вызывать другой метод для Parse
6
ответ дан 7 November 2019 в 11:08
поделиться

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

Выходные параметры упрощают использование.

0
ответ дан 7 November 2019 в 11:08
поделиться

Я думаю, это полезно в ситуациях, когда вам нужно вернуть как логическое значение, так и значение, например TryParse, но было бы хорошо, если бы компилятор позволял что-то вроде этого:

bool isValid = int.TryParse("100", out int result = 0);
3
ответ дан 7 November 2019 в 11:08
поделиться

Определенно, параметры out предназначены для использования, когда у вас есть метод, который должен возвращать более одного значения, в опубликованном вами примере:

public void Do(int arg1, int arg2, out int result)

Нет смысла использовать используйте параметр out, поскольку вы возвращаете только одно значение, и этот метод можно было бы использовать лучше, если бы вы удалили параметр out и поместили возвращаемое значение int:

public int Do(int arg1, int arg2)

В параметрах out есть несколько хороших моментов:

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

В заключение, я в основном пытаюсь использовать параметры out в моем приватном API , чтобы избежать создания отдельных типов для обертывания нескольких возвращаемых значений, и в моем общедоступном API я использую их только в методах, соответствующих шаблону TryParse.

2
ответ дан 7 November 2019 в 11:08
поделиться

Да, в этом есть смысл. Возьмем, к примеру, следующее.

String strNum = "-1";
Int32 outNum;

if (Int32.TryParse(strNum, out outNum)) {
    // success
}
else {
    // fail
}

Что вы могли бы вернуть, если операция завершилась неудачно в нормальной функции с возвращаемым значением? Вы, безусловно, не можете вернуть -1, чтобы представить сбой, потому что тогда не будет различий между значением, возвращаемым при сбое, и фактическим значением, которое было проанализировано с самого начала. Вот почему мы возвращаем логическое значение, чтобы увидеть, удалось ли оно, и если да, то у нас уже есть безопасное значение для нашего «возврата».

0
ответ дан 7 November 2019 в 11:08
поделиться

Меня действительно раздражает, что я не могу пройти in null в параметр out для функций TryParse.

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

0
ответ дан 7 November 2019 в 11:08
поделиться

Я иногда использую параметры out для удобства чтения, когда чтение имени метода более важно, чем какой бы то ни было вывод метода, особенно для методов, которые выполняют команды в дополнение к возвращение результатов.

StatusInfo a, b, c;

Initialize(out a);
Validate(a, out b);
Process(b, out c);

vs.

StatusInfo a = Initialize();
StatusInfo b = Validate(a);
StatusInfo c = Process(b);

По крайней мере, для меня я уделял много внимания первым нескольким символам каждой строки при сканировании. Я легко могу сказать, что происходит в первом примере, после того, как признаю, что объявлены некоторые переменные «StatusInfo». Во втором примере первое, что я вижу, это получение группы StatusInfo. Мне нужно сканировать второй раз, чтобы увидеть, какие эффекты могут иметь методы.

0
ответ дан 7 November 2019 в 11:08
поделиться

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

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

int myoutvalue;
if(int.TryParse("213",out myoutvalue){
    DoSomethingWith(myoutvalue);
}

vs.

ParseResult<int> myoutvalue = int.TryParse("213");
if ( myoutvalue.Success ) {
    DoSomethingWith(myoutvalue.Value);
}

vs.

int? myoutvalue = int.TryParse("213");
if(myoutvalue.HasValue){
    DoSomethingWith(myoutvalue.Value);
}

Что касается «Почему бы не вернуть Nullable Type»: TryParse существует с Framework 1.x, тогда как Nullable Types пришел с 2.0 (поскольку они требуют Generics). Так зачем же излишне нарушать совместимость или начинать вносить несоответствия между TryParse для некоторых типов? Вы всегда можете написать свой собственный метод расширения для дублирования уже существующих функций (см. Сообщение Эрика Липпертса по несвязанной теме, которая включает некоторые аргументы в пользу того, что делать / не делать чего-либо)

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

даже если вы это сделаете, это должно вызвать тревогу, что ваш метод, возможно, делает слишком много. С другой стороны, если ваш метод является чем-то вроде вызова дорогой базы данных или веб-службы, и вы хотите кэшировать результат, это может иметь смысл. Конечно, вы можете создать тип, но, опять же, это означает еще один тип в вашем приложении.

даже если вы это сделаете, это должно вызвать предупреждение о том, что ваш метод, возможно, делает слишком много. С другой стороны, если ваш метод является чем-то вроде вызова дорогой базы данных или веб-службы, и вы хотите кэшировать результат, это может иметь смысл. Конечно, вы можете создать тип, но, опять же, это означает еще один тип в вашем приложении.

0
ответ дан 7 November 2019 в 11:08
поделиться
Другие вопросы по тегам:

Похожие вопросы: