2016-03-25 2 views
1

Ищу для правильного синтаксиса, чтобы использовать неявный оператор в классе, который использует индексатор Асесс частный Словарь:Синтаксис неявного оператора с классом индексатор

[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 } 
+2

Значение 'if (MyClass [k])' должно быть в том, что значение, связанное с ключом, является истинным, а не тем, что ключ существует в коллекции! Что, если значение 'MyClass [k]' существует и было * false *? Это было бы очень запутанно, если бы это выражение считалось истинным. –

+0

Черт! Благодаря! Слишком много думал, что я даже потерял доказательства этого. Еще раз спасибо! – Ulrag

ответ

0

As commenter Eric notes, семантика вашего класса будет полностью нарушена, если вы сможете достичь того, о чем вы просите. Вся точка индексатора такова, что когда вы пишете выражение myClass[anyKey], оно вычисляет значение , которое ваш класс связывает с anyKey.

Если вы должны были изменить реализацию таким образом, чтобы он просто возвращал представляющее сдерживание bool значения, то вы застряли того, чтобы реализовать некоторые другого механизма на самом деле получить значение (например, отдельный метод). Кроме того, это также поставило бы вопрос о том, что должен делать сеттер.

Учитывая, что вы показываете, мне кажется, что письмо if (myClass[anyKey] != null) на самом деле неудобно, и оно кажется мне разумным. То есть, это разумный способ для кода четко выразить свое намерение.

Это сказало, если вы сделали хотите что-то более выразительным, это не было бы неразумно, чтобы написать метод 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 в местный переменная без необходимости при установке значения
  • Имея две разные строки кода, каждая из которых имеет значение установки значения для ключа в словаре
+0

Спасибо! Я думаю, что слишком устал, чтобы увидеть очевидное передо мной на этом. – Ulrag

+0

Бывает.:) Фактически, причина, по которой я написал ответ, заключалась в том, что, когда я рассматривал другие варианты решения вашего вопроса, я продолжал возвращаться к мысли, что, если вы оказались сами, даже если из-за усталости, борясь с проблемой, это возможно, кто-то еще в будущем мог бы и нуждался бы в подобном подталкивании в правильном направлении. Предоставление официального ответа должно помочь обеспечить, чтобы такие люди получали второй взгляд, который им нужен. –