Наиболее эффективный способ проверки типа объекта
Вопрос
У меня есть значения, хранящиеся в виде строк в DataTable
где каждое значение действительно могло бы представлять int
, double
, или string
(все они были преобразованы в строки в процессе импорта из внешнего источника данных).Мне нужно протестировать и посмотреть, к какому типу на самом деле относится каждое значение.
Что более эффективно для приложения (или практической разницы нет)?
- Попробуйте преобразовать в
int
(и тогдаdouble
).Если преобразование сработает, возвратtrue
.Если генерируется исключение, вернитеfalse
. - Регулярные выражения, разработанные в соответствии с шаблоном
int
илиdouble
- Какой-то другой метод?
Решение
Использовал бы double.Попробуйте проанализировать, у него есть преимущества в производительности.
Другие советы
Я бы сказал, не стоит так сильно беспокоиться о такой микроэффективности.Гораздо лучше просто заставить что-то сработать, а затем сделать это как можно более ясным, кратким и легким для чтения.Худшее, что вы можете сделать, - это пожертвовать удобочитаемостью ради незначительного снижения производительности.
В конце концов, лучший способ справиться с проблемами производительности - сохранить их до тех пор, пока у вас не появятся данные, указывающие на наличие реальной проблемы с производительностью...в противном случае вы потратите много времени на микрооптимизацию и фактически увеличите затраты на техническое обслуживание в дальнейшем.
Если вы обнаружите, что эта ситуация с синтаксическим анализом действительно является узким местом в вашем приложении, то самое время попытаться выяснить, каков самый быстрый способ решения проблемы.Я думаю, Джефф (и многие другие) много писал в блогах о подобных вещах.
Вы получите разные результаты для разных методов в зависимости от того, компилируете ли вы с включенной оптимизацией.В принципе, у вас есть несколько вариантов:
object o;
//checking with is
o is int
//check type
o.GetType() != typeof( int )
//cast and catch exception
try{ int j = (int) o; }
catch {}
//use the tryparse
int.TryParse( Convert.ToString( o ), out j )
Вы можете легко настроить консольное приложение, которое пробует каждое из этих 10 000 раз и возвращает длительность для каждого (проверьте, когда o - это int, а когда это что-то другое).
Тот Самый try-catch
метод является самым быстрым, если объект содержит значение int, и, безусловно, самым медленным, если это не так (даже медленнее, чем GetType
). int.TryParse
это довольно быстро, если у вас есть строка, но если у вас есть неизвестный объект, это медленнее.
Интересно, что с .Net 3.5 и включенной оптимизацией o is int
проверка занимает столько же времени, сколько и try-catch
когда o на самом деле является int. o is int
это лишь немного медленнее, если o на самом деле является чем-то другим.
Досадно, что FxCop будет выдавать предупреждения, если вы сделаете что-то вроде:
if( o is int )
int j = (int) o;
Но я думаю, что это ошибка в FxCop - он не знает, что int - это тип значения, и рекомендует вам использовать o as int
вместо этого.
Если ваш ввод всегда представляет собой строку int.TryParse
лучше всего, в противном случае is
оператор самый быстрый.
Поскольку у вас есть строка, я бы посмотрел, нужно ли вам знать, что это int, а не double.Если int.TryParse
проходит, значит, так и будет double.TryParse
таким образом, вы могли бы сократить количество проверок вдвое - возвращать либо double, либо string и уменьшать значение double, когда вы ожидаете int.
Проблема в том, что могут быть ситуации, когда ответ может быть всех трех типов.
3 может быть int, double или string!
Это зависит от того, что вы пытаетесь сделать и насколько важно, чтобы они относились к определенному типу.Возможно, было бы лучше просто оставить их такими, какие они есть, до тех пор, пока вы можете, или, в качестве альтернативы, придумать метод для пометки каждого из них (если у вас есть контроль над источником исходной строки).
Я бы лично использовал int.tryparse , затем double.tryparse.Производительность этих методов довольно высока.Они оба возвращают логическое значение.Если оба завершаются неудачей, то у вас есть строка в соответствии с тем, как вы определили свои данные.