Warning: Cannot use a scalar value as an array in /home/admin/public_html/forum/include/fm.class.php on line 757

Warning: Invalid argument supplied for foreach() in /home/admin/public_html/forum/include/fm.class.php on line 770

Warning: Invalid argument supplied for foreach() in /home/admin/public_html/forum/topic.php on line 737
Форумы портала PHP.SU :: mb_wordwrap [2]

 PHP.SU

Программирование на PHP, MySQL и другие веб-технологии
PHP.SU Портал     На главную страницу форума Главная     Помощь Помощь     Поиск Поиск     Поиск Яндекс Поиск Яндекс     Вакансии  Пользователи Пользователи


 Страниц (2): « 1 [2]   

> Описание: Аналог функции wordwrap для многобайтовых кодировок
armancho7777777 Супермодератор
Отправлено: 10 Мая, 2013 - 21:25:38
Post Id



Активный участник


Покинул форум
Сообщений всего: 4526
Дата рег-ции: Февр. 2011  
Откуда: Москва


Помог: 221 раз(а)




LIME, результат Вашего кода:

Тут много текстааааааааааа
аааааааааааааааааааааааааа
аааааааааааааааааааа, кото
рый надо разбить на части
по 26 символов с учётом пр

А должно получиться:

Тут много
текстааааааааааааааааааааа
аааааааааааааааааааааааааа
аааааааааа, который надо
разбить на части по 26
символов с учётом пробелов.


Исходная строка:
$str = 'Тут много текстааааааааааааааааааааааааааааааааааааааааааааааааааааааааа, который надо разбить на части по 26 символов с учётом пробелов.';

Обрыв должен осуществляться с учётом не только указанной длины но и пробелов.
Но если указан четвёртый аргумент функции,
то при превышении длины слова указанного значения,
строка обрывается на предыдущем пробеле
с последующим обрывом слова на каждом отрезке
в соответсвии с указанной длиной
пока не встретит следующий пробел.

(Отредактировано автором: 10 Мая, 2013 - 21:38:35)

 
 Top
OrmaJever
Отправлено: 11 Мая, 2013 - 00:01:54
Post Id



Активный участник


Покинул форум
Сообщений всего: 7540
Дата рег-ции: Янв. 2010  
Откуда: Чернигов


Помог: 299 раз(а)




armancho7777777 пишет:
Так выложите код, который выполнит задачу так же, как стандартная функция wordwrap с использованием функций (конструкций), отличных от регулярок.

Ну так мне это не интересно, я просто за 2 минуты написал пример работы с использованием цикла, первое что пришло в голову. На крайний случай я могу полностью переписать функцию wordwrap из Си на php, но код получится большим и неоправданым. Если решили резать регуляркой то режьте, тут не кто не против, я даже за.
(Добавление)
armancho7777777 пишет:
LIME, результат Вашего кода:

Я только что проверил, и ваша функция так же этого не делает.


-----
Если вы хотя бы 3-4 раза не решите всё выкинуть и начать заново - вы явно что-то делаете не так.
 
 Top
esterio
Отправлено: 11 Мая, 2013 - 00:44:12
Post Id



Активный участник


Покинул форум
Сообщений всего: 5025
Дата рег-ции: Нояб. 2012  
Откуда: Украина, Львов


Помог: 127 раз(а)




завтра если найду у себя на компе брошу код
 
 Top
armancho7777777 Супермодератор
Отправлено: 11 Мая, 2013 - 08:27:35
Post Id



Активный участник


Покинул форум
Сообщений всего: 4526
Дата рег-ции: Февр. 2011  
Откуда: Москва


Помог: 221 раз(а)




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

А я и писал Выше, что пошёл дорабатывать.
 
 Top
armancho7777777 Супермодератор
Отправлено: 11 Мая, 2013 - 10:47:26
Post Id



Активный участник


Покинул форум
Сообщений всего: 4526
Дата рег-ции: Февр. 2011  
Откуда: Москва


Помог: 221 раз(а)




Всё, функция готова:

PHP:
скопировать код в буфер обмена
  1.  
  2. function mb_wordwrap($str, $width = 74, $break = "\r\n", $cut = false)
  3. {
  4.         $width = $width | 1;
  5.  
  6.         return preg_replace_callback(
  7.        
  8.                 '~(?P<str>' . ($cut ? '[^\s]{1,' . $width . '}\s*' :
  9.                 '.{1,' . $width . '}?\S+(?=\s+\S+)') . ')~mus',
  10.                
  11.                 function($match) use ($width, $break, $cut, &$res)
  12.                 {
  13.                         if(mb_strlen($res . trim($match['str'])) > $width)
  14.                         {
  15.                                 $str = $res . ((empty($res) || preg_match('~^(\s*<br\s*/?\s*>\s*)$~', $match['str'])) ? '' : $break);
  16.                                 $res = $match['str'];
  17.                                 return $str;
  18.                         }
  19.                        
  20.                         $res .= $match['str'];
  21.                 },
  22.                 $str
  23.         );     
  24. }
  25.  

(Отредактировано автором: 11 Мая, 2013 - 12:10:04)

 
 Top
armancho7777777 Супермодератор
Отправлено: 11 Мая, 2013 - 13:16:22
Post Id



Активный участник


Покинул форум
Сообщений всего: 4526
Дата рег-ции: Февр. 2011  
Откуда: Москва


Помог: 221 раз(а)




Чёрт... Опять местами глючит Хм
 
 Top
OrmaJever
Отправлено: 11 Мая, 2013 - 13:38:24
Post Id



Активный участник


Покинул форум
Сообщений всего: 7540
Дата рег-ции: Янв. 2010  
Откуда: Чернигов


Помог: 299 раз(а)




я бы написал уже, но упёрся наверное в элементарное. Как получить символ в юникоде? ведь $str[0] это может быть и пол символа и символ. Подскажите функцию которая мне будет символы выдавать, сделаю ;)


-----
Если вы хотя бы 3-4 раза не решите всё выкинуть и начать заново - вы явно что-то делаете не так.
 
 Top
LIME
Отправлено: 11 Мая, 2013 - 13:41:39
Post Id


Активный участник


Покинул форум
Сообщений всего: 10732
Дата рег-ции: Нояб. 2010  


Помог: 322 раз(а)




да в мануале полно примеров
armancho7777777 то что в итоге не будет глючить получится не менее громоздким чем в мануале
причем почти уверен что по сути повторит одно из решений
 
 Top
armancho7777777 Супермодератор
Отправлено: 11 Мая, 2013 - 14:24:12
Post Id



Активный участник


Покинул форум
Сообщений всего: 4526
Дата рег-ции: Февр. 2011  
Откуда: Москва


Помог: 221 раз(а)




Короче, некогда заморачиваться.
Потом может будет время, доделаю.
Пока выкавырял из зенда, удалив лишнее чуток Радость

PHP:
скопировать код в буфер обмена
  1.  
  2.  
  3. function mb_wordwrap($string, $width = 75, $break = "\n", $cut = false)
  4. {
  5.      $stringWidth = mb_strlen($string);
  6.      $breakWidth  = mb_strlen($break);
  7.  
  8.      $result    = '';
  9.      $lastStart = $lastSpace = 0;
  10.  
  11.      for ($current = 0; $current < $stringWidth; $current++)
  12.          {
  13.          $char = mb_substr($string, $current, 1);
  14.  
  15.          if ($breakWidth === 1)
  16.                  $possibleBreak = $char;
  17.                  else
  18.                  $possibleBreak = mb_substr($string, $current, $breakWidth);
  19.  
  20.          if ($possibleBreak === $break)
  21.                  {
  22.              $result    .= mb_substr($string, $lastStart, $current - $lastStart + $breakWidth);
  23.              $current   += $breakWidth - 1;
  24.              $lastStart  = $lastSpace = $current + 1;
  25.          }
  26.                  elseif ($char === ' ')
  27.                  {
  28.              if ($current - $lastStart >= $width)
  29.                          {
  30.                  $result    .= mb_substr($string, $lastStart, $current - $lastStart) . $break;
  31.                  $lastStart  = $current + 1;
  32.              }
  33.  
  34.              $lastSpace = $current;
  35.          }
  36.                  elseif ($current - $lastStart >= $width && $cut && $lastStart >= $lastSpace)
  37.                  {
  38.              $result    .= mb_substr($string, $lastStart, $current - $lastStart) . $break;
  39.              $lastStart  = $lastSpace = $current;
  40.          }
  41.                  elseif ($current - $lastStart >= $width && $lastStart < $lastSpace)
  42.                  {
  43.              $result    .= mb_substr($string, $lastStart, $lastSpace - $lastStart) . $break;
  44.              $lastStart  = $lastSpace = $lastSpace + 1;
  45.          }
  46.      }
  47.  
  48.      if ($lastStart !== $current)
  49.          $result .= mb_substr($string, $lastStart, $current - $lastStart);
  50.  
  51.      return $result;
  52. }
  53.  


P.S. Уверен, можно написать покороче.

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

(Отредактировано автором: 11 Мая, 2013 - 15:29:10)

 
 Top
OrmaJever
Отправлено: 11 Мая, 2013 - 14:32:09
Post Id



Активный участник


Покинул форум
Сообщений всего: 7540
Дата рег-ции: Янв. 2010  
Откуда: Чернигов


Помог: 299 раз(а)




armancho7777777 пишет:
P.S. В сети есть решения, но какие-то громоздкие.

armancho7777777 пишет:
Короче, некогда заморачиваться.
Спойлер (Отобразить)

Хи Может всётаки стоило взять "громоздкие" решения из сети?))

(Отредактировано автором: 11 Мая, 2013 - 14:35:41)



-----
Если вы хотя бы 3-4 раза не решите всё выкинуть и начать заново - вы явно что-то делаете не так.
 
 Top
LIME
Отправлено: 11 Мая, 2013 - 14:36:24
Post Id


Активный участник


Покинул форум
Сообщений всего: 10732
Дата рег-ции: Нояб. 2010  


Помог: 322 раз(а)




armancho7777777 а здесь не смотрел?
http://www.php.net/manual/ru/fun...ion.wordwrap.php
и с регулярками есть и без
 
 Top
armancho7777777 Супермодератор
Отправлено: 11 Мая, 2013 - 14:54:35
Post Id



Активный участник


Покинул форум
Сообщений всего: 4526
Дата рег-ции: Февр. 2011  
Откуда: Москва


Помог: 221 раз(а)




LIME, ну как-же не смотрел.
OrmaJever пишет:
Может всётаки стоило взять "громоздкие" решения из сети?))

Да не говори....
Злой сижу ...
Столько времени впустую убил.
 
 Top
LIME
Отправлено: 11 Мая, 2013 - 14:57:16
Post Id


Активный участник


Покинул форум
Сообщений всего: 10732
Дата рег-ции: Нояб. 2010  


Помог: 322 раз(а)




armancho7777777 пишет:
Столько времени впустую убил.
девиз велосипедистов))
 
 Top
armancho7777777 Супермодератор
Отправлено: 11 Мая, 2013 - 15:07:20
Post Id



Активный участник


Покинул форум
Сообщений всего: 4526
Дата рег-ции: Февр. 2011  
Откуда: Москва


Помог: 221 раз(а)




LIME, да не, это не причём.
Просто уверен, что можно компактнее написать, но ещё пока не мастер регулярок, оставил на потом ))
 
 Top
OrmaJever
Отправлено: 11 Мая, 2013 - 15:18:29
Post Id



Активный участник


Покинул форум
Сообщений всего: 7540
Дата рег-ции: Янв. 2010  
Откуда: Чернигов


Помог: 299 раз(а)




armancho7777777 пишет:
         $char = mb_substr($string, $current, 1);

Вот что мне нужно было узнать! Растерялся
Пока сижу пома подумаю над своим вариантом.


-----
Если вы хотя бы 3-4 раза не решите всё выкинуть и начать заново - вы явно что-то делаете не так.
 
 Top
Страниц (2): « 1 [2]
Сейчас эту тему просматривают: 0 (гостей: 0, зарегистрированных: 0)
« Пользовательские функции »


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



Powered by PHP  Powered By MySQL  Powered by Nginx  Valid CSS  RSS

 
Powered by ExBB FM 1.0 RC1. InvisionExBB