Unity中C#字符串与枚举比较及自定义Contains实现咨询
完美解决枚举与字符串关联的Contains检测问题
哈哈,这个需求我太熟了!C#枚举确实没法直接给成员赋值字符串,但咱们可以用特性+扩展方法的组合来实现你的目标——让字符串的Contains方法直接接收枚举成员,自动映射到对应的字符串去检测,完全不用手动写字符串常量!
我给你拆解成一步步的实现方案,直接套到你的Unity代码里就行:
步骤1:定义绑定字符串的自定义特性
首先咱们需要一个特性类,用来给每个枚举成员“挂”上对应的字符串值:
using System; // 自定义特性,用来存储枚举对应的字符串值 [AttributeUsage(AttributeTargets.Field)] public class StringValueAttribute : Attribute { public string Value { get; } public StringValueAttribute(string value) { Value = value; } }
步骤2:给你的BeadColor枚举加上特性
现在把你想要的字符串值绑定到枚举成员上:
public enum BeadColor { [StringValue("P")] BLUE, [StringValue("B")] RED, // 这里可以继续加其他枚举成员和对应的字符串 }
步骤3:写枚举的扩展方法,获取对应的字符串
接下来写一个静态扩展方法,帮我们把枚举成员转换成对应的字符串:
using System.Reflection; public static class EnumExtensions { // 获取枚举成员绑定的字符串值 public static string GetStringValue(this Enum enumValue) { // 获取枚举成员的FieldInfo FieldInfo fieldInfo = enumValue.GetType().GetField(enumValue.ToString()); // 获取特性 StringValueAttribute attribute = fieldInfo.GetCustomAttribute<StringValueAttribute>(); // 如果没有加特性,这里可以抛出异常或者返回默认值,根据你的需求调整 if (attribute == null) throw new InvalidOperationException($"枚举成员 {enumValue} 未绑定字符串值"); return attribute.Value; } }
步骤4:给string写扩展方法,支持枚举参数的Contains
这就是你要的核心功能了——让string的Contains能直接接收枚举:
public static class StringExtensions { // 扩展string的Contains方法,支持传入BeadColor枚举 public static bool Contains(this string source, BeadColor beadColor) { // 先把枚举转成对应的字符串,再调用原生Contains if (string.IsNullOrEmpty(source)) return false; string targetString = beadColor.GetStringValue(); return source.Contains(targetString); } }
步骤5:结合你的现有代码使用
现在回到你的CustomClass和MainClass,调用起来就跟你想的一样简单:
你的CustomClass示例(调整后)
public class CustomClass { public string BigRoadData { get; private set; } private readonly string[] strData = { "P", "B", "P", "P", "B" }; public CustomClass() { // 构建BigRoadData的逻辑不变 BigRoadData = string.Join("", strData); } }
MainClass里的调用
public class MainClass { public void Test() { CustomClass custom = new CustomClass(); // 直接传入枚举成员,检测是否包含对应的字符串 bool hasBlue = custom.BigRoadData.Contains(BeadColor.BLUE); // 会返回true,因为BigRoadData里有"P" bool hasRed = custom.BigRoadData.Contains(BeadColor.RED); // 也会返回true,因为有"B" Debug.Log($"包含蓝色珠子对应的字符串:{hasBlue}"); Debug.Log($"包含红色珠子对应的字符串:{hasRed}"); } }
一些小提醒
- 如果你怕有些枚举成员忘记加特性,可以在
GetStringValue里返回枚举的ToString()作为 fallback,而不是抛出异常,根据你的业务需求调整就行。 - 扩展方法要放在静态类里,并且命名空间要能被你的Unity脚本访问到(比如放在全局命名空间,或者你项目常用的命名空间下)。
- 如果需要忽略大小写的检测,可以在扩展方法里调用
source.IndexOf(targetString, StringComparison.OrdinalIgnoreCase) >= 0来替代原生的Contains。
这样一来,你就完全不用直接写字符串常量了,所有的映射都通过枚举和特性来管理,代码可读性和可维护性都高了不少!
内容的提问来源于stack exchange,提问作者Ginxxx
相关产品推荐
相关产品推荐

