public static List <TEntry> ToList <TEntry>(this DataTable dataTable)
            where TEntry : new()
        {
            var type    = typeof(TEntry);
            var columns = dataTable.Columns;
            var actions = new Dictionary <string, Action <object, object> >();

            foreach (DataColumn c in columns)
            {
                var columnName = c.ColumnName;
                var action     = DynamicPropertyAccessor.CreateSetPropertyValueAction
                                 (
                    typeof(TEntry)
                    , columnName
                                 );
                actions[columnName] = action;
            }
            List <TEntry> list = null;
            var           rows = dataTable.Rows;

            foreach (DataRow r in rows)
            {
                var entry = new TEntry();
                if (list == null)
                {
                    list = new List <TEntry>();
                }
                foreach (DataColumn c in columns)
                {
                    var columnName = c.ColumnName;
                    var v          = r[columnName];
                    if (!DBNull.Value.Equals(v))
                    {
                        var action = actions[columnName];
                        action(entry, v);
                    }
                }
                list.Add(entry);
            }
            return(list);
        }
        private static Dictionary <string, PropertyAccessor> GetTypePropertiesAccessors(Type type)
        {
            var properties = type.GetProperties();
            Dictionary <string, PropertyAccessor> dictionary = null;

            Array.ForEach
            (
                properties
                , (x) =>
            {
                if (
                    _typesWhiteList.Any
                    (
                        (xx) =>
                {
                    return(xx == x.PropertyType);
                }
                    )
                    )
                {
                    var accessor = new PropertyAccessor()
                    {
                        Getter = DynamicPropertyAccessor.CreateGetPropertyValueFunc(type, x.Name)
                        ,
                        Setter = DynamicPropertyAccessor.CreateSetPropertyValueAction(type, x.Name)
                        ,
                        Property = x
                    };
                    if (dictionary == null)
                    {
                        dictionary = new Dictionary <string, PropertyAccessor>();
                    }
                    dictionary.Add(x.Name, accessor);
                }
            }
            );
            return(dictionary);
        }
        public static void AttachPerformanceCountersToProperties <T>
        (
            string performanceCounterInstanceName
            , string category
            , T target                             //= default(T)
        )
        {
            var type           = typeof(T);
            var propertiesList = type.GetProperties().ToList();

            propertiesList = propertiesList
                             .Where
                             (
                (pi) =>
            {
                var parameters = pi.GetIndexParameters();
                return
                (
                    pi.PropertyType == typeof(PerformanceCounter) &&
                    (parameters == null ? 0 : parameters.Length) <= 0
                );
            }
                             ).ToList();
            if (PerformanceCounterCategory.Exists(category))
            {
                propertiesList
                .ForEach
                (
                    (pi) =>
                {
                    if (PerformanceCounterCategory.CounterExists(pi.Name, category))
                    {
                        if (PerformanceCounterCategory.InstanceExists(performanceCounterInstanceName, category))
                        {
                            //var pc = new PerformanceCounter(category, pi.Name, instanceName, false);
                            //pc.InstanceName = instanceName;
                            //pc.RemoveInstance();
                        }
                    }
                }
                );
                //PerformanceCounterCategory.Delete(category);
            }
            if (!PerformanceCounterCategory.Exists(category))
            {
                var ccdc = new CounterCreationDataCollection();
                propertiesList
                .ForEach
                (
                    (pi) =>
                {
                    var propertyName           = pi.Name;
                    var performanceCounterType = PerformanceCounterType.NumberOfItems64;
                    var performanceCounterName = propertyName;
                    var attribute
                        = pi
                          .GetCustomAttributes(false)
                          .FirstOrDefault
                          (
                              (x) =>
                    {
                        return
                        (x as PerformanceCounterDefinitionAttribute
                         != null);
                    }
                          ) as PerformanceCounterDefinitionAttribute;
                    if (attribute != null)
                    {
                        var counterName = attribute.CounterName;
                        if (!string.IsNullOrEmpty(counterName))
                        {
                            performanceCounterName = counterName;
                        }
                        var counterType = attribute.CounterType;
                        //if (counterType != null)
                        {
                            performanceCounterType = counterType;
                        }
                    }
                    var ccd = PerformanceCountersHelper
                              .GetCounterCreationData
                              (
                        performanceCounterName
                        , performanceCounterType
                              );
                    ccdc.Add(ccd);
                }
                );
                PerformanceCounterCategory
                .Create
                (
                    category
                    , string.Format("{0} Category Help.", category)
                    , PerformanceCounterCategoryType.MultiInstance
                    , ccdc
                );
            }
            propertiesList.ForEach
            (
                (pi) =>
            {
                var propertyName           = pi.Name;
                var performanceCounterType = PerformanceCounterType.NumberOfItems64;
                var performanceCounterName = propertyName;
                var attribute
                    = pi
                      .GetCustomAttributes(false)
                      .FirstOrDefault
                      (
                          (x) =>
                {
                    return
                    (x as PerformanceCounterDefinitionAttribute
                     != null);
                }
                      ) as PerformanceCounterDefinitionAttribute;
                if (attribute != null)
                {
                    var counterName = attribute.CounterName;
                    if (!string.IsNullOrEmpty(counterName))
                    {
                        performanceCounterName = counterName;
                    }
                    var counterType = attribute.CounterType;
                    //if (counterType != null)
                    {
                        performanceCounterType = counterType;
                    }
                }
                var pc = new PerformanceCounter()
                {
                    CategoryName = category
                    ,
                    CounterName = performanceCounterName
                    ,
                    InstanceLifetime = PerformanceCounterInstanceLifetime.Process
                    ,
                    InstanceName = performanceCounterInstanceName
                    ,
                    ReadOnly = false
                    ,
                    RawValue = 0
                };
                if (pi.GetGetMethod().IsStatic)
                {
                    var setter = DynamicPropertyAccessor
                                 .CreateSetStaticPropertyValueAction <PerformanceCounter>
                                 (
                        type
                        , propertyName
                                 );
                    setter(pc);
                }
                else
                {
                    if (target != null)
                    {
                        var setter = DynamicPropertyAccessor
                                     .CreateSetPropertyValueAction <PerformanceCounter>
                                     (
                            type
                            , propertyName
                                     );
                        setter(target, pc);
                    }
                }
            }
            );
        }