Regex для приема только персидских символов

Я работаю над формой, в которой один из них пользовательский валидатор должен принимать только персидские символы... Я использовал следующий код:

    var myregex = new Regex(@"^[\u0600-\u06FF]+$");
    if (myregex.IsMatch(mytextBox.Text))
    {
        args.IsValid = true;
    }
    else
    {
        args.IsValid = false;
    }

но кажется, что он работает только для проверки арабских символов, и он не охватывает все персидские символы (ему не хватает этих четырех گ, چ, پ, ژ)... есть ли способ решить эту проблему?

Ответы

Ответ 1

TL; DR

Farsi ДОЛЖЕН использовать наборы символов:

  • Используйте ^[آابپتثجچحخدذرزژسشصضطظعغفقکگلمنوهی]+$ для писем или используйте ^[آابپتثجچحخدذرزژسشصضطظعغفقکگلمنوهی]+$ относительно вашего аромата регулярного выражения (не все \uXXXX поддерживают \uXXXX):

    ^[\u0622\u0627\u0628\u067E\u062A-\u062C\u0686\u062D-\u0632\u0698\u0633-\u063A\u0641\u0642\u06A9\u06AF\u0644-\u0648\u06CC]+$
    
  • Используйте ^[۰۱۲۳۴۵۶۷۸۹]+$ для чисел или относительно вашего регулярного выражения:

    ^[\u06F0-\u06F9]+$
    
  • Используйте [ ‬ٌ ‬ًّ ‬َ ‬ِ ‬ُ ‬ْ ‬] для гласных или в отношении вашего регулярного выражения:

    [\u202C\u064B\u064C\u064E-\u0652]
    

или их комбинации. Возможно, вы захотите добавить другие арабские буквы, такие как Hamza ء к вашему набору символов дополнительно.

Почему [\u0600-\u06FF] и [آ-ی] ошибочны?

Хотя \u0600-\u06FF включает в себя:

  • گ с 06AF
  • چ с кодовым 0686
  • پ с 067E
  • ژ с 0698

также все ответы, которые предполагают, что [\u0600-\u06FF] или [آ-ی] просто НЕПРАВИЛЬНЫ.

т.е. \u0600-\u06FF содержит 209 символов, чем вам нужно! и он также включает числа!

enter image description here

Вся история

Этот ответ существует, чтобы исправить распространенное заблуждение. Codepoints с 0600 по 06FF не обозначают алфавит персидского/фарси (также [آ-ی]):

[\u0600-\u0605 ؐ-ؚ\u061Cـ ۖ-\u06DD ۟-ۤ ۧ ۨ ۪-ۭ ً-ٕ ٟ ٖ-ٞ ٰ ، ؍ ٫ ٬ ؛ ؞ ؟ ۔ ٭ ٪ ؉ ؊ ؈ ؎ ؏
۞ ۩ ؆ ؇ ؋ ٠۰ ١۱ ٢۲ ٣۳ ٤۴ ٥۵ ٦۶ ٧۷ ٨۸ ٩۹ ءٴ۽ آ أ ٲ ٱ ؤ إ ٳ ئ ا ٵ ٮ ب ٻ پ ڀ
ة-ث ٹ ٺ ټ ٽ ٿ ج ڃ ڄ چ ڿ ڇ ح خ ځ ڂ څ د ذ ڈ-ڐ ۮ ر ز ڑ-ڙ ۯ س ش ښ-ڜ ۺ ص ض ڝ ڞ
ۻ ط ظ ڟ ع غ ڠ ۼ ف ڡ-ڦ ٯ ق ڧ ڨ ك ک-ڴ ػ ؼ ل ڵ-ڸ م۾ ن ں-ڽ ڹ ه ھ ہ-ۃ ۿ ەۀ وۥ ٶ
ۄ-ۇ ٷ ۈ-ۋ ۏ ى يۦ ٸ ی-ێ ې ۑ ؽ-ؿ ؠ ے ۓ \u061D]

255 символов падают под арабского блока (0600-06FF), фарси алфавит состоит из 32 букв, которые в дополнение к фарси демонстрации цифр было бы 42. Если мы добавим гласные (арабский гласные первоначально, которые редко используются в фарси) без Tanvin ً, ٍِ ‬ ٌ ‬ и Tashdid (ّ ‬, которые являются подмножеством арабского диакритиками не фарси, мы бы в конечном итоге с 46 символов. Это означает, что \u0600-\u06FF содержит 209 символов, чем вам нужно!

۷ с 06F7 является фарси-представлением числа 7 и ٧ с 06F7 номером 0667 является арабским представлением того же числа. ۶ - представление фарси числа 6 и ٦ - арабское представление того же числа. И все они находятся в коде с 0600 по 06FF.

Формы персидских цифр четыре (۴), пять (۵) и шесть (۶) отличаются от форм, используемых на арабском языке, а другие числа имеют разные кодовые точки.

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

[آ-ی] содержит также 117 символов, что намного больше, чем то, что нужно для проверки. Вы можете увидеть их все с помощью Unicode CLDR.

Ответ 2

В вашем регулярном выражении есть стандартный диапазон арабских символов. Для дополнительных символов вам нужно добавить их в регулярное выражение отдельно. Вот их коды:

ژ \u0698
پ \u067E
چ \u0686
گ \u06AF

Итак, у всех вас должно быть

^[\u0600-\u06FF\u0698\u067E\u0686\u06AF]+$

Ответ 3

В дополнение к принятому ответу (fooobar.com/questions/331043/...) мы должны рассмотреть также символы Zero-width_non-joiner (или نیم فاصله в персидских). К сожалению, у нас есть 2 символа. Один из них является стандартным, а другой не является стандартным, но широко используется:

Таким образом, окончательный может быть:

^[\u0600-\u06FF\uFB8A\u067E\u0686\u06AF\u200C\u200F]+$

Если вы хотите рассмотреть " space", вы можете использовать это:

^[\u0600-\u06FF\uFB8A\u067E\u0686\u06AF\u200C\u200F ]+$

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

/^[\u0600-\u06FF\uFB8A\u067E\u0686\u06AF7\u200C\u200F ]+$/.test('ای‌پسر تو چه می‌دانی؟')

Ответ 4

Внимание: persianRex написан на Javascript, однако вы можете использовать исходный код и скопировать вставку символов

Обнаружение персидских символов - сложная задача из-за разнообразия раскладок клавиатуры и операционных систем. Раньше я столкнулся с такой же проблемой, и я решил написать библиотеку с открытым исходным кодом, чтобы исправить эту проблему.

вы можете исправить свою проблему следующим образом: persianRex.text.test(yourInput); // возвращает true или false

вот полная документация: http://imanmh.github.io/persianRex/

Ответ 5

Фарси, Дари и Таджик вышли из моего бэйливика, но немного порываясь в кодовых диаграммах Юникода, говорит мне, что арабский язык охватывает 5 блоков кода Юникода:

Вы можете получить в них (по крайней мере некоторые из них) в регулярных выражениях, используя именованные блоки вместо явных диапазонов кодовой точки: \p{IsArabicPresentationForms-A} даст вам четвертый блок Unicode в предыдущем списке.

Вы также можете прочитать персидские вычисления в Юникоде: http://behdad.org/download/Publications/persiancomputing/a007.pdf

Ответ 6

Я не могу читать фарси, но посмотрите, есть ли у одного из дополнений арабского юникода буквы, которые вы ищете.

http://www.unicode.org/charts/

Ответ 7

Именованные блоки, например \p {Arabic}, охватывают весь арабский script, а не только персидские символы.

Формы представления (u + FB50-u + FDFF) не должны использоваться в тексте и должны быть преобразованы в стандартный диапазон (u + 0600-u + 06FF).

Чтобы покрыть только персидский язык, нам нужно следующее:

  • Подмножество символов Фарси из стандартного арабского диапазона, т.е. (U + 0621-U + 0624, U + 0626-U + 063A, U + 0641-U + 0642, U + 0644-U + 0648)
  • Стандартная арабская диакритика (U + 064B-U + 0652)
  • Две дополнительные диакритики (U + 0654, U + 0670)
  • 4 дополнительных символов фарси "گ چ پ ژ" (U + 067E, U + 0686, U + 0698, U + 06AF)
  • U + 06A9: персидский каф (формально: "арабское письмо Кехх", разные обозначения из арабского кафа)
  • U + 06CC: Farsi Yeh (другое обозначение от арабского Yeh)
  • U + 200C: Zero-Width-Non-Joiner

Итак, полученное регулярное выражение будет:

^[\u0621-\u0624\u0626-\u063A\u0641-\u0642\u0644-\u0648\u064B-\u0652\u067E\u0686\u0698\u06AF\u06CC\u06A9\u0654\u670\u200c}]+$

См. также символы примера для персидского языка, перечисленные здесь:

http://unicode.org/cldr/trac/browser/trunk/common/main/fa.xml

Ответ 8

Я не уверен, что regex - это способ сделать это, однако проблема не специфична только для персидских или арабских, китайских, русского текста. так что, возможно, вы могли бы увидеть, существует ли символ в вашей Codepage, если не на кодовой странице, то я сомневаюсь, что пользователь может вставить их с помощью устройства ввода.

 var encoding = Encoding.GetEncoding(1256);
 var expect = "گ چ پ ژ";
 var actual= encoding.GetBytes("گ چ پ ژ");
 Assert.AreEqual(encoding.GetString(actual),expect);

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