очень странная строка уникальная проблема в C # - PullRequest
2 голосов
/ 11 августа 2009

Я использую VSTS2008 + C # + .Net 3.0. Вот мой код и соответствующее исключение из ADO.Net. Вот мой ввод двух строк в двоичной и текстовой форме, есть идеи, что не так? Почему две разные строки будут рассматриваться как один и тот же ADO.Net?

Сообщение об исключении:

An unhandled exception of type 'System.Data.ConstraintException' occurred in System.Data.dll

Additional information: Column 'Name' is constrained to be unique.  Value '������' is already present.

Ввод строк в двоичном и текстовом виде:

alt text

alt text

StackOverflow не отображается правильно для моего кода для строк here, вот снимок экрана для того, как он фактически выглядит в моем редакторе VSTS 2008.

alt text

Мой код:

    static void Main(string[] args)
    {
        string[] buf = new string[] { "����", "������" };

        CompareInfo ci = System.Globalization.CultureInfo.InvariantCulture.CompareInfo;
        ci.Compare(buf[0], buf[1], CompareOptions.IgnoreWidth);
        Console.WriteLine (String.Compare(buf[0], buf[1], StringComparison.InvariantCultureIgnoreCase));

        DataTable bulkInserTable = new DataTable("BulkRequestTable");
        bulkInserTable.CaseSensitive = true;
        DataColumn column = null;
        DataRow row = null;

        // add Keyword column to datatable
        column = new DataColumn();
        column.DataType = System.Type.GetType("System.String");
        column.ColumnName = "Name";
        column.ReadOnly = true;
        column.Unique = true;
        bulkInserTable.Columns.Add(column);

        foreach (string item in buf)
        {
            row = bulkInserTable.NewRow();
            row["Name"] = item;
            bulkInserTable.Rows.Add(row);
        }
    }

Ответы [ 6 ]

4 голосов
/ 11 августа 2009

Я видел, что вы использовали InvariantCulture в своем сравнении. Для сравнения вы должны использовать Ordinal (буквенное сравнение букв и символов) или CurrentCulture (который заменяет объекты - например, = === AE).

Возможно, вам повезет больше, если ввести символы в виде строк символов Юникода, например:

string text = "\uEFBF\uBDEF\uBFBD\uEFBF";
string text2= "\uEFBF\uBD0D\uAEFB\uFBDE\uFBFB";

У меня есть некоторые китайские / японские иероглифы (не вставляются полностью):

string text = "뷯뾽";
string text2 = "봍껻ﯞﯻ";

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

2 голосов
/ 11 августа 2009

Это похоже на метки порядка байтов (BOM) - http://en.wikipedia.org/wiki/Byte_order_mark

Спецификации, вероятно, лишены при сравнении, следовательно, они будут такими же?

1 голос
/ 11 августа 2009

Не уверен, в каком шрифте или наборе символов находятся эти классные персонажи, но, похоже, они не очень хорошо сортируются. Метод Compare () основан на сортируемости строк, поэтому культура очень важна для сравнения строк, чувствительных к культуре. Эти строки символов не возвращаются как отличающиеся от сортировки, поэтому они фактически "одинаковы". Метод String.Equals () покажет их как разные.

buf[0].Equals(buf[1]) = false

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

1 голос
/ 11 августа 2009

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

0 голосов
/ 12 августа 2009

Ваша проблема, вероятно, связана с тем, что ваш персонаж является специальным символом Юникода.

"The replacement character � (often a black diamond with a white question mark)
is a symbol found in the Unicode standard at codepoint U+FFFD in the Specials 
table. It is used to indicate problems when a system such as a text parser was
not able to decode a stream of data to a correct symbol"

http://en.wikipedia.org/wiki/Unicode_Specials

0 голосов
/ 11 августа 2009

возможно, отключить ограничение уникальности dataTable и реализовать свой собственный уникальный метод проверки?

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