Анализ и обработка чисел
Национальный формат и страна будут очень важны, когда дело дойдет до взаимо¬действия с числами и датами, хранящимися в виде строк. Представьте получение стро¬кового буфера со встроенным числом и последующую попытку выполнения сложения, как проиллюстрировано на рис. 3.13.
Сумма чисел — это, конечно, математическая операция. Когда операция сложения выполняется для строк, она всегда приводит к конкатенации буферов. Суммирование — самый простой способ конкатенации строковых буферов.
Однако конкатенация — это не цель примера. Его задача в том, чтобы превратить строки в числа, а затем сложить их, чтобы переменная с содержала значение 3 (1 + 2 = 3). Переделанная версия примера приведена на рис. 3.14. Этот код анализирует строку как целое число.
Тип int обладает методом Parse (), применяемым для преобразования строки в це¬лое число. Анализ срабатывает, только если буфер содержит допустимое число. Если буфер содержит символы или недопустимое число, произойдет ошибка.
Чтобы код мог справиться с неудачным преобразованием строк, решение, исполь¬зуемое функциями анализа, заключается в создании исключения, которое программа могла бы обработать. В качестве альтернативы отказоустойчивый способ анализа чисел без блока исключения подразумевал бы использование метода TryParse О , как в сле¬дующем примере.
Метод TryParse () не возвращает целочисленного значения, он возвращает логи¬ческий (bool) флаг (истина (true) или ложь (false)), указывающий на возможность анализа буфера. Если возвращено значение true, то буфер можно проанализировать, а результат сохранить в значении параметра, помеченного идентификатором out. Идентификатор out используется в среде .NET для указания на то, что параметр содержит значение после вызова метода TryParse О . Вы можете проанализировать числа других типов, используя те же методы (например, float. TryParse ()).
Существует множество возможных вариантов анализа чисел. Например, число "100" может быть проанализировано как шестнадцатеричное. (Компьютеры могут использо¬вать шестнадцатеричные числа. Шестнадцатеричная форма записи (hexadecimal) зача¬стую называется шестнадцатеричным кодом (hex) для краткости.) Вот пример шестнад-цатеричного преобразования.
using System.Globalization;
public void ParseHexadecimal () {
int value = int.Parse ("100", NumberStyles.HexNumber); }
Этот пример использует тот вариант метода Parse (), который имеет второй, до-полнительный параметр, представляющий формат числа. В данном случае второй па-раметр указывает, что формат числа шестнадцатеричный (NumberStyles .HexNumber, из пространства имен System. Globalization). В примере буфер представляет десятич¬ное число 256, которое проверяется с помощью метода Assert .AreEquals ().
На заметку. Если вас интересует вопрос, как 100 превращается в 256 на шестнадцатеричном уровне, используйте калькулятор операционной системы Windows. Переведите калькулятор в инженерный вид, щелкните на переключателе Hex, введите число 100, а затем щелкните на переключателе Dec.
Перечисление NumberStyles имеет другие значения, применяемые для анализа чис¬ла по другим правилам. Например, некоторые правила считают круглые скобки вокруг числа указанием на отрицательное значение. Другие правила относятся к отступам. Например.
public void TestParseNegativeValue () { int value = int.Parse ( " (10) ",
NumberStyles.AllowParentheses
NumberStyles.AllowLeadingWhite |
NumberStyles.AllowTrailingWhite); }
Число4 " (10) "в этом примере намеренно усложнено, оно имеет отступ и кру¬глые скобки. Попытка анализировать число с помощью метода Parse () без приме¬нения значений перечисления NumberStyles не сработает. Значение перечисления AllowParentheses разрешает обрабатывать круглые скобки, AllowLeadingWhite — игнорировать предваряющие пробелы, a AllowTrailingWhite — завершающие. После обработки буфера в переменной value будет сохранено значение -10.
Другие значения перечисления NumberStyles позволяют учитывать десятичные точ-ки дробных чисел, положительные или отрицательные числа и т.д. Это поднимает тему заработки чисел, отличных от типа int. Каждый из базовых типов данных (boolean, ~yte и double) имеет собственные версии методов Parse () и TryParse (). Кроме того, метод TryParse () также может использовать перечисление NumberStyles. (Более под¬робная информация о значениях перечисления NumberStyles приведена в документа¬ми MSDN.)
Анализ целочисленных значений осуществляется одинаково, независимо от страны, а вот анализ дат или типа double — нет. Рассмотрим следующий пример, в котором осу¬ществляется попытка проанализировать буфер, содержащий десятичное значение.
public void TestDoubleValue () { double value = double.Parse("1234 . 56" ) ; value = double.Parse("1,234.56"); }
В обоих случаях этого примера метод Parse () используется для преобразования чис¬ла 1234,56. В первом случае анализ прост, поскольку число содержит лишь десятичную точку, отделяющую целые значения от десятичных. Во втором случае анализ усложнен, поскольку число содержит запятую, отделяющую тысячи от целого числа. В обоих слу¬чаях метод Parse () сработает нормально.
Если вы проверите этот код, то, возможно, получите исключение. В этом случае ви¬новат национальный формат приложения. Числа в примере предназначены для форма¬та en-СА, английский Канада.