То, что нужно помнить о десятичном разделителе

Изменение разделителей в Microsoft Windows

У одного крупного международного заказчика в рамках проэкта переинсталяции под глобальные стандрарты, на рабочих станциях были развернуты английские версии Microsoft Windows. 

Работая с CSV пользователи столкнулись с проблемой некорректного отображения данных и, как обычно в таких случаях, начали винить ИТшников  ̶в̶о̶ ̶в̶с̶е̶х̶ ̶т̶я̶ж̶к̶и̶х̶ ̶г̶р̶е̶х̶а̶х̶  в простоях в работе

Значения смешивались в ячейках, и информация была действительно нечитаема.  Дело заключалось в том, что для русского Excel разделителем является  ;  (точка с запятой), а везде ( см. стандарт RFC 4180)  ,  (запятая). Microsoft Windows дает возможность изменять разделитель элементов списков. На стационарной машине его можно изменить Панель Управления (Control Panel) — Язык и региональные стандарты (Region and Language)  – Форматы (Formats)  — Дополнительные параметры (Additional settings) — Разделитель элементов списка (List separator) Но в случае с множеством рабочих мест и наличием домена AD менять руками настройки на каждом компьютере не интересно и грешно. Через групповые политики данное значение изменяется по пути :User ConfigurationPreferencesControl Panel SettingsRegionals Options  В области Regional Options кликаем правое кнопкой мыши New Regional Options. В появившемся окне выбираем вкладку Numbers  и изменяем значение List separator Важно, что измененный символ будет использоваться системой и, соответственно, всеми приложениями системы.Все, кто когда-либо писали программы на C#, использовали такую простую функцию как

Convert.ToDouble(string value);

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

В англоязычных странах в качестве разделителя используется точка, а в остальных странах, преимущественно, запятая. Всё в принципе, не плохо, и среда .Net, как и большинство современных программ знают, какой именно разделитель используется системой. Но такая программа, как Meta Trader была написана русскими программистами, которые о разделителе как-раз таки не знали, и программа всегда использует по умолчанию запятую. Нужно было реализовать передачу с MT4 на приложение данных и обратно через сокеты. Во время тестирования у себя на компьютере странного поведения замечено не было, т.к. у меня в системе стоит по умолчанию “,”. Но программа писалась для иностранного заказчика, у которого по идее всё должно было работать точно также. Непонятно по какой причине, данные, принимаемые моей программой, при переводе из строки в Double обрабатывались не правильно и без всяких исключений. Например, преобразование из строки «1,4174» в число у меня на компьютере давало такой же результат, в то время как у заказчика «1,4174» давало результат 14174, то есть пятизначное число без всяких разделителей, которое было замечено не сразу. Решение, в отличие от самой ошибки было найдено моментально – заменить запятую, на знак, используемый системой. Строки:

 String Source = "0,05"; Double number = Convert.ToDouble(Source); 

вызывают FormatException в случае если разделителем в системе выступает точка. Заменяем их на

 Char separator = System.Globalization.CultureInfo.CurrentCulture.NumberFormat.CurrencyDecimalSeparator[0]; String Source = "0,05".Replace( ',' , separator); Double number = Convert.ToDouble(Source); 

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

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

  • https://www.tune-it.ru/web/fender/blog/-/blogs/252050
  • https://habr.com/post/138957/

Оцените статью
Рейтинг автора
5
Материал подготовил
Илья Коршунов
Наш эксперт
Написано статей
134
Добавить комментарий