fork download
  1. <?php
  2.  
  3.  
  4. function getLetterCounts($word)
  5. {
  6. return array(
  7. 'cyr' => preg_match_all('/[а-яё]/ui', $word),
  8. 'lat' => preg_match_all('/[a-z]/i', $word)
  9. );
  10. }
  11.  
  12. $latToCyr = array(
  13. 'a' => 'а', 'c' => 'с', 'e' => 'е', 'o' => 'о', 'p' => 'р', 'x' => 'х',
  14. 'y' => 'у', 'k' => 'к', 'm' => 'м', 't' => 'т', 'h' => 'н', 'b' => 'в',
  15. 'A' => 'А', 'B' => 'В', 'C' => 'С', 'E' => 'Е', 'H' => 'Н', 'K' => 'К',
  16. 'M' => 'М', 'O' => 'О', 'P' => 'Р', 'T' => 'Т', 'X' => 'Х', 'Y' => 'У'
  17. );
  18. $cyrToLat = array_flip($latToCyr);
  19.  
  20. $text = <<<EOF
  21. Администрация объявляет конкурс на поставку кaнцелярских тoваров
  22. на сумму 100500 руб.
  23. EOF;
  24.  
  25. $matches = array();
  26. preg_match_all('/[а-яёa-z]+/ui', $text, $matches);
  27.  
  28. foreach ($matches[0] as $word) {
  29. $counts = getLetterCounts($word);
  30.  
  31. if ($counts['cyr'] == 0 || $counts['lat'] == 0) {
  32. continue;
  33. }
  34.  
  35. if ($counts['cyr'] >= $counts['lat']) {
  36. $marked = preg_replace('/[a-z]/i', '[$0]', $word, 1);
  37. } else {
  38. $marked = preg_replace('/[а-яё]/ui', '[$0]', $word, 1);
  39. }
  40.  
  41. echo "Опечатка в слове {$word}: {$marked}\n";
  42. }
  43.  
  44. $fixedText = preg_replace_callback('/[а-яёa-z]+/ui', function ($match) use ($latToCyr, $cyrToLat) {
  45. $word = $match[0];
  46. $counts = getLetterCounts($word);
  47.  
  48. if ($counts['cyr'] == 0 || $counts['lat'] == 0) {
  49. return $word;
  50. }
  51.  
  52. if ($counts['cyr'] >= $counts['lat']) {
  53. return strtr($word, $latToCyr);
  54. }
  55.  
  56. return strtr($word, $cyrToLat);
  57. }, $text);
  58.  
  59. echo "Исправленный текст:\n{$fixedText}\n";
Success #stdin #stdout 0.02s 26440KB
stdin
Standard input is empty
stdout
Опечатка в слове кaнцелярских: к[a]нцелярских
Опечатка в слове тoваров: т[o]варов
Исправленный текст:
Администрация объявляет конкурс на поставку канцелярских товаров
на сумму 100500 руб.