О string.Intern в C # - PullRequest
       0

О string.Intern в C #

2 голосов
/ 27 ноября 2011

Какую ситуацию мне нужно назвать string.Intern или string.IsInterned на String значении?

У меня есть этот метод, используемый сеткой для группировки строк:

    // get grouping value for DataGrid
    string GroupItemAccessor(object value)
    {
        COA coa = (COA)value;
        return string.IsInterned(coa.GroupName);
    }

Если я не позвоню string.Intern результат неправильный, эта сетка должна сгруппироваться по значению GroupName.

String.Intern not used

Это если string.Intern использовал (как пример кода), он работает как я ожидал.

String.Intern used

Ответы [ 3 ]

4 голосов
/ 27 ноября 2011

Причина, по которой вы получаете другой результат, заключается в том, что вы группируете не по строковому значению, а по групповой ссылке.При группировании строки обрабатываются не как строки, а как объекты, поэтому сравниваются только ссылки, а не содержимое.

Когда вы читаете значения из базы данных, каждая строка будет отдельным экземпляром, даже еслиони имеют одинаковую ценность.Например, первые две строки «AAA» будут отдельными объектами, а не ссылками на один и тот же объект.

Если вы не можете создать группу сетки для значений строки, использование String.Intern является одним из способовстроки одинаковы, так что группировка работает в любом случае.

Однако вы можете использовать свой собственный метод создания строк одинаковых экземпляров, поскольку интернирование строк означает, что они никогда не будут собираться мусором.Вы можете использовать класс следующим образом:

public class LocalIntern {

  private Dictionary<string, string> _intern = new Dictionary<string, string>();

  public string Intern(string value) {
    if (_intern.ContainsKey(value)) {
      return _intern[value];
    } else {
      _intern.Add(value, value);
      return value;
    }
  }

}

Когда вы снова заполняете сетку, вы просто создаете новый объект LocalIntern, и строки, содержащиеся в предыдущем, можно собирать мусором.

1 голос
/ 27 ноября 2011

Если бы я предполагаю, то я бы сказал, что сетка использует равенство ссылок. Насколько мне известно, интернализуются только буквальные строки.

Таким образом, без интернирования coa.GroupName, два одинаковых имени группы не являются ссылочными равными, и, следовательно, не сетка, кажется, обрабатывает их по-разному.

1 голос
/ 27 ноября 2011

По предположению, SuperList, вероятно, выполняет проверку идентичности для группировки (проверка ссылок) - если это действительно так, строки, которые не были интернированы, будут считаться различными, даже если они являются одной и той же строкой.

В таком случае строки должны быть интернированы для правильной группировки элемента управления.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...