带有 class 索引器的隐式运算符的语法
Syntax for implicit operator with class indexer
我正在寻找在使用索引器访问私有字典的 class 上使用隐式运算符的正确语法:
[System.Serializable]
public class MyClass : IEnumerable
{
private Dictionary<string, object> vars = new Dictionary<string, object>();
public object this[string key]
{
get
{
if(vars.ContainsKey(key))
{
return (object)vars[key];
}
else
{
return null;
}
}
set
{
object o = value;
if(!vars.ContainsKey(key))
{
vars.Add(key, o);
}
else if(value == null)
{
vars.Remove(key);
}
else
{
vars[key] = o;
}
}
}
/*some code*/
public static implicit operator bool(WorldVars w, string i)
{
if(w[i] != null)
{
return true;
}
else
{
return false;
}
}
}
现在使用非常简单
MyClass[anykey] = myValue
但我想实现一种更快的方法来测试值的存在,例如:
if(MyClass[anykey])
{ //logic }
,如果您能够实现您所要求的,您的 class 的语义将被完全破坏。索引器的全部意义在于,当您编写表达式 myClass[anyKey]
时,它的计算结果为您的 class 与 anyKey
关联的 值 。
如果您要更改实现,使其仅返回一个 bool
值表示包含,那么您将不得不实现一些 other 机制来实际上检索值(例如,一个单独的方法)。此外,它还会引发 setter 应该做什么的问题。
鉴于您展示的实现,在我看来,编写 if (myClass[anyKey] != null)
并不是真的不方便,而且对我来说似乎是合理的表达方式。也就是说,它是代码明确表达其意图的合理方式。
就是说,如果您确实想要更具表现力的东西,那么在您的 class 中编写一个 ContainsKey()
方法并不是没有道理的:
public bool ContainsKey(string key) { return vars.ContainsKey(key); }
然后您可以像这样检查密钥是否存在:
if (myClass.ContainsKey[anyKey]) { ... }
最后,您发布的代码应该可以很好地工作,但对我来说似乎过于冗长且不一致。恕我直言,编写索引器方法的更好方法是这样的:
public object this[string key]
{
get
{
object o;
return vars.TryGetValue(key, out o) ? o : null;
}
set
{
if (value != null)
{
vars[key] = value;
}
else
{
vars.Remove(key);
}
}
}
该实现避免了以下情况:
- 获取值时对包含进行冗余检查
- 设置值时不必要地将
value
复制到局部变量
- 有两行不同的代码,每行都具有为字典中的键设置值的效果
我正在寻找在使用索引器访问私有字典的 class 上使用隐式运算符的正确语法:
[System.Serializable]
public class MyClass : IEnumerable
{
private Dictionary<string, object> vars = new Dictionary<string, object>();
public object this[string key]
{
get
{
if(vars.ContainsKey(key))
{
return (object)vars[key];
}
else
{
return null;
}
}
set
{
object o = value;
if(!vars.ContainsKey(key))
{
vars.Add(key, o);
}
else if(value == null)
{
vars.Remove(key);
}
else
{
vars[key] = o;
}
}
}
/*some code*/
public static implicit operator bool(WorldVars w, string i)
{
if(w[i] != null)
{
return true;
}
else
{
return false;
}
}
}
现在使用非常简单
MyClass[anykey] = myValue
但我想实现一种更快的方法来测试值的存在,例如:
if(MyClass[anykey])
{ //logic }
myClass[anyKey]
时,它的计算结果为您的 class 与 anyKey
关联的 值 。
如果您要更改实现,使其仅返回一个 bool
值表示包含,那么您将不得不实现一些 other 机制来实际上检索值(例如,一个单独的方法)。此外,它还会引发 setter 应该做什么的问题。
鉴于您展示的实现,在我看来,编写 if (myClass[anyKey] != null)
并不是真的不方便,而且对我来说似乎是合理的表达方式。也就是说,它是代码明确表达其意图的合理方式。
就是说,如果您确实想要更具表现力的东西,那么在您的 class 中编写一个 ContainsKey()
方法并不是没有道理的:
public bool ContainsKey(string key) { return vars.ContainsKey(key); }
然后您可以像这样检查密钥是否存在:
if (myClass.ContainsKey[anyKey]) { ... }
最后,您发布的代码应该可以很好地工作,但对我来说似乎过于冗长且不一致。恕我直言,编写索引器方法的更好方法是这样的:
public object this[string key]
{
get
{
object o;
return vars.TryGetValue(key, out o) ? o : null;
}
set
{
if (value != null)
{
vars[key] = value;
}
else
{
vars.Remove(key);
}
}
}
该实现避免了以下情况:
- 获取值时对包含进行冗余检查
- 设置值时不必要地将
value
复制到局部变量 - 有两行不同的代码,每行都具有为字典中的键设置值的效果