构建翻译器封装字典提可读性,KeyValuePair密封类继承问题求助
嘿,这个问题我之前在项目里也遇到过——KeyValuePair确实是密封类,没法直接继承它来封装你的单条翻译项。不过有几个实用的方案能帮你实现想要的封装效果,咱们一步步来看:
方案1:用组合替代继承(最推荐)
既然不能继承KeyValuePair,咱们可以把它作为SingleTranslation类的内部字段来使用,通过暴露属性的方式对外提供访问,这样既能复用KeyValuePair的逻辑,又能自定义自己的类结构。
示例代码:
public class SingleTranslation { private readonly KeyValuePair<string, string> _translationPair; // 构造函数初始化键值对 public SingleTranslation(string identifier, string translatedText) { _translationPair = new KeyValuePair<string, string>(identifier, translatedText); } // 对外暴露标识符和翻译文本的只读属性 public string Identifier => _translationPair.Key; public string TranslatedText => _translationPair.Value; // 可选:重写ToString方便调试和日志输出 public override string ToString() { return $"[{Identifier}] -> {TranslatedText}"; } }
这个方案的好处是:
- 保留了KeyValuePair的原生逻辑,不用自己重复实现键值对的基础功能
- 可以在
SingleTranslation里轻松扩展额外功能,比如加个TranslationLanguage属性、或者验证输入的方法 - 封装性更好,不会暴露KeyValuePair的内部细节
方案2:完全自定义单条翻译类
如果不想依赖KeyValuePair,完全可以自己写一个独立的SingleTranslation类,这样灵活性更高,完全不受KeyValuePair的限制。
示例代码:
public class SingleTranslation { // 定义你需要的属性,这里直接用业务命名更清晰 public string Identifier { get; } public string TranslatedText { get; } // 构造函数可以加参数验证,避免无效数据 public SingleTranslation(string identifier, string translatedText) { Identifier = identifier ?? throw new ArgumentNullException(nameof(identifier), "标识符不能为空"); TranslatedText = translatedText ?? throw new ArgumentNullException(nameof(translatedText), "翻译文本不能为空"); } // 可选:实现IEquatable接口,方便集合中的比较操作 public bool Equals(SingleTranslation other) { if (other is null) return false; return Identifier == other.Identifier && TranslatedText == other.TranslatedText; } public override bool Equals(object obj) => Equals(obj as SingleTranslation); public override int GetHashCode() => HashCode.Combine(Identifier, TranslatedText); }
这个方案适合你以后可能需要给单条翻译添加更多业务属性的场景(比如翻译来源、创建时间),完全由你掌控类的结构和行为。
关于Translation类的小建议
你原来想通过class Translation : Dictionary<string,string>{}来封装字典,其实也可以考虑用组合替代继承——因为Dictionary的公共方法很多,继承后会暴露所有这些方法,可能不符合你想要的封装性。
比如改成这样:
public class Translation { private readonly Dictionary<string, string> _translationStore = new Dictionary<string, string>(); // 只暴露你需要的方法,比如添加单条翻译 public void Add(SingleTranslation translation) { if (translation == null) throw new ArgumentNullException(nameof(translation)); _translationStore.Add(translation.Identifier, translation.TranslatedText); } // 获取翻译的方法,或者用索引器更方便 public string this[string identifier] { get => _translationStore[identifier]; set => _translationStore[identifier] = value; } // 可选:获取所有翻译项的方法 public IEnumerable<SingleTranslation> GetAllTranslations() { return _translationStore.Select(kv => new SingleTranslation(kv.Key, kv.Value)); } }
这样你可以严格控制对外暴露的功能,避免误用Dictionary的其他方法,同时也能更好地适配你自定义的SingleTranslation类。
总的来说,组合而非继承是解决这类密封类封装问题的核心思路,既能满足你的可读性需求,又能保证代码的灵活性和扩展性。
内容的提问来源于stack exchange,提问作者narancha
相关产品推荐
相关产品推荐

