为枚举解析器编写泛型方法

本文关键字:泛型方法 枚举 | 更新日期: 2023-09-27 18:36:07

我有两个方法在做类似的功能。我想将这两者合并为一个,这样代码就不会重复。

第一种方法:

private string GetPlanogramStatusListString()
        {
            string outValue = null;
            if (this.POGSelectedStatusList != null)
            {
                outValue = "";
                // Parse the string list to get enum values into a list
                List<string> tempStatusList = new List<string>();
                foreach (object sts in this.POGSelectedStatusList)
                {                    
                    PogStoreData.PlanogramStatusCode enumValue;
                    if (Enum.TryParse<PogStoreData.PlanogramStatusCode>(sts.ToString(), out enumValue))
                    {
                        tempStatusList.Add(((int)enumValue).ToString());
                    }
                }
                outValue = string.Join(",", tempStatusList);
            }
            return outValue;
        }

第二种方法:

private string GetMoveStatusListString()
        {
            string outValue = null;
            if (this.POGMovedStatus != null)
            {
                outValue = "";
                // Parse the string list to get enum values into a list
                List<string> tempStatusList = new List<string>();
                foreach (object sts in this.POGMovedStatus)
                {
                    PogStoreData.POGMovedStatus enumValue;
                    if (Enum.TryParse<PogStoreData.POGMovedStatus>(sts.ToString(), out enumValue))
                    {
                        tempStatusList.Add(((int)enumValue).ToString());
                    }
                }
                outValue = string.Join(",", tempStatusList);
            }
            return outValue;
        }

我想将这两种方法合并为一种方法。我该怎么做?

为枚举解析器编写泛型方法

我实际上已经编译并运行了这段代码:

private string GetEnumListString<T>(IEnumerable list) where T : struct
{
    string outValue = null;
    if (list != null)
    {
        outValue = "";
        // Parse the string list to get enum values into a list
        List<string> tempStatusList = new List<string>();
        foreach (object sts in list)
        {                    
            T enumValue;
            if (Enum.TryParse(sts.ToString(), out enumValue))
            {
                tempStatusList.Add((Convert.ToInt32(enumValue)).ToString());
            }
        }
        outValue = string.Join(",", tempStatusList);
    }
    return outValue;
}
private string GetPlanogramStatusListString()
{
    return GetEnumListString<PogStoreData.PlanogramStatusCode>(this.POGSelectedStatusList);
}
private string GetMoveStatusListString()
{
    return GetEnumListString<PogStoreData.POGMovedStatus>(this.POGMovedStatus);
}

它编译并生成与原始代码相同的输出。

由于将对象列表转换为整数字符串列表并不直接绑定到类,因此可以使用扩展方法来处理这种逻辑。尽管对象类型的好处有限。

此外,您在这里所做的实际上是映射/过滤/减少。这意味着您可以稍微缩短代码,并对这些操作使用标准 LINQ 名称。(映射/过滤/减少转换为.Net Select/Where/Aggregate)

        public static string ToIntegers<T>(this IEnumerable<object> values) where T : struct
        {
            return values?.Select(x => {
                T enumValue;
                return Enum.TryParse(x.ToString(), out enumValue) ? Convert.ToInt32(enumValue).ToString() : null;
            })
            .Where(x => x != null)
            .Aggregate((s1, s2) => s1 + "," + s2);
        }

LINQ 在方便和不可读之间跨越界限是个人品味的问题。对于习惯于"映射/过滤/减少"的人来说,这可能很容易阅读,而对于其他人来说则不是这样。我只是想提供一些其他意见,因为目前的答案非常相似。

像这样的东西?

private string GetsListString<T>(List<object> list)
{
    string outValue = null;
    if (list != null)
    {
        outValue = "";
        // Parse the string list to get enum values into a list
        List<string> tempStatusList = new List<string>();
        foreach (object sts in list)
        {
            T enumValue;
            if (Enum.TryParse<T>(sts.ToString(), out enumValue))
            {
                tempStatusList.Add(((int)enumValue).ToString());
            }
        }
        outValue = string.Join(",", tempStatusList);
    }
    return outValue;
}

您可以使用类似于以下代码的内容,

        private string GetMoveStatusListString<T>(IEnumerable list) where T : struct 
        {
            string outValue = null;
            if (list != null)
            {
                outValue = "";
                // Parse the string list to get enum values into a list
                List<string> tempStatusList = new List<string>();
                foreach (object sts in list)
                {
                    T enumValue;
                    if (Enum.TryParse<T>(sts.ToString(), out enumValue))
                    {
                        tempStatusList.Add(enumValue.ToString());
                    }
                }
                outValue = string.Join(",", tempStatusList);
            }
            return outValue;
        }

一行代码就足够了:

string GetStatusList(IEnumerable<object> array) 
{
    return string.Join(",", array.Select((e)=>(Convert.ToInt32(e)).ToString()) );
}

用作

// GetPlanogramStatusListString();
var x=GetStatusList(POGSelectedStatusList.ToArray());
// 1,2,2
// GetMoveStatusListString();
var y=GetStatusList(POGMovedStatus.ToArray());
// 2,3,2,1,2