Подтвердить что ты не робот

Определение имени символа Unicode в .Net

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

Если нет, есть ли библиотека, которая может это сделать?

4b9b3361

Ответ 1

Теперь это проще, чем когда-либо, так как есть пакет в nuget с именем Информация о Unicode

С этим вы можете просто позвонить:

UnicodeInfo.GetName(character)

Ответ 2

Вот решение, которое вы можете реализовать сразу, например copy/paste/compile.

Сначала загрузите базу данных Юникода (UCD) здесь: http://www.unicode.org/Public/UNIDATA/UnicodeData.txt

Затем добавьте этот код в свой проект, чтобы прочитать UCD и создать словарь для поиска имени значения .NET char:

string[] unicodedata = File.ReadAllLines( "UnicodeData.txt", Encoding.UTF8 );
Dictionary<char,string> charname_map = new Dictionary<char,string>( 65536 );
for (int i = 0; i < unicodedata.Length; i++)
{
    string[] fields = unicodedata[i].Split( ';' );
    int char_code = int.Parse( fields[0], NumberStyles.HexNumber );
    string char_name = fields[1];
    if (char_code >= 0 && char_code <= 0xFFFF) //UTF-16 BMP code points only
    {
        bool is_range = char_name.EndsWith( ", First>" );
        if (is_range) //add all characters within a specified range
        {
            char_name = char_name.Replace( ", First", String.Empty ); //remove range indicator from name
            fields = unicodedata[++i].Split( ';' );
            int end_char_code = int.Parse( fields[0], NumberStyles.HexNumber );
            if (!fields[1].EndsWith( ", Last>" ))
                throw new Exception( "Expected end-of-range indicator." );
            for (int code_in_range = char_code; code_in_range <= end_char_code; code_in_range++)
                charname_map.Add( (char)code_in_range, char_name );
        }
        else
            charname_map.Add( (char)char_code, char_name );
    }
}

Файл UnicodeData.txt кодируется в кодировке UTF-8 и состоит из одной строки информации для каждой кодовой точки Юникода. Каждая строка содержит список полей, разделенных запятыми, где первое поле является кодовой точкой Юникода в шестнадцатеричной форме (без префиксов), а второе поле - это имя символа. Информацию о файле и других полях, которые содержатся в каждой строке, можно найти здесь: Информацию о формате UCD можно найти здесь: http://www.unicode.org/reports/tr44/#Format_Conventions

Как только вы используете приведенный выше код для построения сопоставления символов с именами символов, вы просто извлекаете их с карты примерно так:

char c = 'Â';
string character_name;
if (!charname_map.TryGetValue( c, out character_name ))
    character_name = "<Character Name Missing>"; //character not found in map
//character_name should now contain "LATIN CAPITAL LETTER A WITH CIRCUMFLEX";

Я предлагаю встраивать файл UnicodeData.txt в ваши ресурсы приложения и переносить этот код в класс, который загружает и анализирует файл один раз в статическом инициализаторе. Чтобы сделать код более читаемым, вы можете реализовать метод расширения в классе char 'класса, например "GetUnicodeName". Я намеренно ограничил значения диапазоном от 0 до 0xFFFF, потому что это может быть все UTF-16.NET char..NET char на самом деле не представляет собой истинный "символ" (также называемый кодовой точкой), а скорее код юникода UTF-16, так как некоторые "символы" на самом деле требуют двух блоков кода. Такая пара кодовых единиц называется высоким и низким суррогатом. Значения выше 0xFFFF (наибольшее значение, которое может хранить 16 бит char) находятся за пределами базовой многоязычной плоскости (BMP), и в соответствии с кодировкой UTF-16 требуется два char для кодирования. Отдельные коды, которые являются частью суррогатной пары, будут иметь такие имена, как "Non Private Use High Surrogate", "Private Survey Surprited" и "Low Surrogate" с этой реализацией.

Ответ 3

Если вы используете Process Monitor для просмотра файлов, к которым обращается charmap.exe, вы увидите, что он открывает файл с именем C:\Windows\system32\getuname.dll. Этот файл содержит имена символов в его ресурсах (фактически сами ресурсы находятся в файле .mui в подкаталоге, специфичном для культуры).

Итак, все, что вам нужно сделать, это получить имена из этого файла, используя API LoadString. Я написал вспомогательный класс для этого:

public class Win32ResourceReader : IDisposable
{
    private IntPtr _hModule;

    public Win32ResourceReader(string filename)
    {
        _hModule = LoadLibraryEx(filename, IntPtr.Zero, LoadLibraryFlags.AsDataFile | LoadLibraryFlags.AsImageResource);
        if (_hModule == IntPtr.Zero)
            throw Marshal.GetExceptionForHR(Marshal.GetHRForLastWin32Error());
    }

    public string GetString(uint id)
    {
        var buffer = new StringBuilder(1024);
        LoadString(_hModule, id, buffer, buffer.Capacity);
        if (Marshal.GetLastWin32Error() != 0)
            throw Marshal.GetExceptionForHR(Marshal.GetHRForLastWin32Error());
        return buffer.ToString();
    }

    ~Win32ResourceReader()
    {
        Dispose(false);
    }

    public void Dispose()
    {
        Dispose(true);
        GC.SuppressFinalize(this);
    }

    public void Dispose(bool disposing)
    {
        if (_hModule != IntPtr.Zero)
            FreeLibrary(_hModule);
        _hModule = IntPtr.Zero;
    }

    [DllImport("user32.dll", CharSet = CharSet.Auto, SetLastError = true)]
    static extern int LoadString(IntPtr hInstance, uint uID, StringBuilder lpBuffer, int nBufferMax);

    [DllImport("kernel32.dll", CharSet = CharSet.Auto, SetLastError = true)]
    static extern IntPtr LoadLibraryEx(string lpFileName, IntPtr hReservedNull, LoadLibraryFlags dwFlags);

    [DllImport("kernel32.dll", CharSet = CharSet.Auto, SetLastError = true)]
    static extern bool FreeLibrary(IntPtr hModule);

    [Flags]
    enum LoadLibraryFlags : uint
    {
        AsDataFile = 0x00000002,
        AsImageResource = 0x00000020
    }
}

Вы можете использовать его следующим образом:

string path = @"C:\Windows\System32\getuname.dll";
using (var reader = new Win32ResourceReader(path))
{
    string name = reader.GetString(0xA9);
    Console.WriteLine(name); // Copyright Sign
}

Ответ 4

Это не встроенная функция .NET. Вы можете узнать из Charmap.exe, он отображает имя кодовой страницы в строке состояния. Если вам это нужно в вашей собственной программе, вы можете скомпилировать Unicode Character Database в своем приложении. Остерегайтесь авторских прав.

Ответ 6

Как отмечают NoBugz и MichaelBray.net Не предоставляйте встроенную функцию для получения Юникода имени символов.

И вам нужно использовать из базы данных символов Юникода, которые предоставляют bUnicode.o в http://unicode.org/ucd сегодня, которая содержит полную информацию обо всех Unicode 5.2 информация о символах (приложение № 44)

Другой альтернативой является использование символов в виде символов. Вы можете получить доступ к нему через Start\App Programs\Accessories\System Tools\Character Map (win + R = > charmap)

А также вы можете использовать из инструментов конвертера Unicode, который является инструментом с открытым исходным кодом в http://unicode.codeplex.com, он также предоставляет пользовательский интерфейс для получения информации, а также ее использование из UCD Unicode (приложение № 44), основная часть этого программного обеспечения для вас - это то, что вы указали в EnterPriseAppUnit dll этого приложения для вашей апликации и использования из предоставленного API.

эта сборка содержит статический метод, который дает Char и возвращает имя, шестнадцатеричный код, десятичный код и т.д.