Я понимаю, что это не выдает Исключение, и из-за этого это могло бы быть красивым быстрее, но также и, Вы, скорее всего, используете его для преобразования входа в данные, которые можно использовать, таким образом, я не думаю, что это используется так часто для создания что большая часть различия в терминах производительности.
Так или иначе примеры, которые я видел, все время по строкам если/еще блок с TryParse
, еще возврат сообщения об ошибке. И мне, это - в основном то же самое как использование блока попытки/выгоды с выгодой, возвращая сообщение об ошибке.
Так, я пропускаю что-то? Существует ли ситуация, где это на самом деле полезно?
Это довольно просто: используйте Parse
, если вы хотите исключение при обнаружении недопустимых данных; в противном случае используйте TryParse
.Таким образом, ваш вопрос выглядит следующим образом:
Почему вам не нужно исключение, если данные недействительны?
Исключения следует использовать только в исключительных случаях, и недопустимые данные не могут быть исключительным случаем. Возможно, вы пишете программу очистки данных, которая ожидает получить недопустимые данные и будет пытаться вывести разумное значение, когда данные недействительны. Возможно, данные не так уж и важны, и вы можете просто пропустить запись, которая их содержит.
Это зависит от контекста, и выбор методов Parse
и TryParse
позволяет выбрать подходящий для вас механизм синтаксического анализа.
Ну, int.TryParse возвращает логическое значение, позволяющее проверить, было ли оно успешным, вместо того, чтобы перехватывать исключение. Я обычно использую его в ситуациях, когда, если информация была успешно переведена, я хочу ее использовать, но если нет, это не важно, я могу игнорировать сбой, поскольку я хочу использовать значение по умолчанию, если я не получу значимого значение, и в этом случае я заменю его, но если значение не имеет смысла, я оставлю значение по умолчанию.
Теория гласит, что исключения по своей природе дороги, и поэтому вы не должны использовать их, чтобы диктовать ход выполнения программы. Вы должны поймать их там, где что-то семантически неверно, а не то, что может быть интерпретировано как поток данных.
Для случаев, когда либо не возражаете против установки значения 0 при неудачном синтаксическом анализе (возможно, недопустимый ввод), либо случаев, когда вам нужна краткость, код возврата TryParse позволяет это.
Каждый раз, когда вам нужно выполнить синтаксический анализ, он обходится дешевле, чем исключение, к тому же вы можете сделать его частью простого if Оператор вместо большого блока try ... catch.
Я не обезьяна C #, но ...
Исключение прерывает нормальный поток кода, передавая обработку блоку catch.
TryParse предоставит вам больше возможностей управления (например, выделит ошибку в текстовом поле) вместо того, чтобы полагаться на механизм исключений.
Если вы выполняете проверку ввода в форме, вы можете установить ErrorProvider для элемента управления (или MessageBox, или какое-либо другое уведомление), когда он возвращает false. Это не исключительный случай, потому что, как говорили другие, вы должны спланировать это.
Помимо аспекта производительности, о котором вы сами упомянули, есть еще и семантическая разница:
Использование try/catch предназначено для исключительных обстоятельств. Ввод некорректных данных - это то, чего вы ожидаете, а не что-то исключительное.
Если вам нужно установить значение по умолчанию при неудачном разборе, TryParse вместе с if - отличный способ сделать это.
По возможности используйте TryParse
- его использование намного дешевле, чем создание исключения.
Предположим, вы читаете файл журнала:
public IEnumerable<LogEntry> GetAllValidEntries() {
while (!logReader.Finished) {
string nextLine = logReader.ReadLine();
LogEntry nextEntry;
if (TryParseLogEntry(nextLine, out nextEntry))
yield return nextEntry;
}
}
private bool TryParseLogEntry(string line, out LogEntry logEntry) {
logEntry = null;
if (string.IsNullOrEmpty(line))
return false;
string[] cells = line.Split(';');
if (cells.Length < 3)
return false;
DateTime time;
decimal price;
int quantity;
// We just want to read this line of text as a LogEntry
// IF it is valid; otherwise, there's no reason to throw
// an error in the user's face
if (!DateTime.TryParse(cells[0], out time) ||
!decimal.TryParse(cells[1], out price) ||
!int.TryParse(cells[2], out quantity))
return false;
logEntry = new LogEntry(time, price, quantity);
return true;
}
Поскольку вся цель приведенного выше кода - извлечь допустимые элементы из последовательности (которая предположительно ожидается, что он будет содержать некоторые недопустимые элементы), я думаю, что методы TryParse
делают в этом случае много больше смысла, чем методы Parse
, которые требуют действительный ввод.