У вебмастеров иногда возникает задача укоротить длинные URL, которые вводят в форму участники форумов. Из-за длинных ссылок расползается дизайн страниц. Предположим, кто-то отослал на форум такой текст:
Рекомендую посетить: http://www.lsafhwoeufqfsjvdkghalhasdghasglhasgl.com/fasfasfasdf/
На самом деле ссылка может оказаться еще длинее. В HTML-коде страницы форума эта ссылка должна появиться в виде URL:
Рекомендую посетить: <a href="http://www.lsafhwoeufqfsjvdkghalhasdghasglhasgl.com/fasfasfasdf/" target="_blank"> http://www.lsafhwoeufqfsjvdkghalhasdghasglhasgl.com/fasfasfasdf/</a>
Внутри тега a ссылку, естественно, обрезать не надо, тем более, что в видимом тексте ее не будет, а вот то, что стоит перед тегом </a>, будет видно, и если это "слово" будет слишком длинным, то это может испортить дизайн. Надо после 50-го символа такой ссылки вставить три точки и получить такой текст:
Рекомендую посетить: <a href="http://www.lsafhwoeufqfsjvdkghalhasdghasglhasgl.com/fasfasfasdf/" target="_blank"> http://www.lsafhwoeufqfsjvdkghalhasdghasglhasgl.co…</a>
Другие длинные слова (не ссылки) надо также урезать. Мало ли что может ввести пользователь… Я нашел такое решение:
s/(\A|\s)(?!href=")(\S{50})\S+/$1$2.../g;
Предполагаем, что текст находится в переменной $_. Регулярное выражение начинает поиск от начала текста и каждого пробельного символа. Если после этого не стоит фрагмент href=, то проверяется, есть ли после этого "слово" длиной 50 символов, после которого стоит непробельный символ. Если да, то происходит замена всего, что найдено на $1 - пробельный символ перед длинным "словом", 50 символов с начала этого "слова" на $1, эти же 50 символов с начала длинного "слова", а последующие непробельные символы заменяются на три точки. Если бы в начале шаблона вместо (\A|\s) стояло просто (\s), то длинное "слово", стоящее в самом начале текста, не было бы укорочено.
Вот еще один вариант с использованием кода Perl в части замены:
s/((\S{50})\S+)/index($1,'href=') > -1 ? $1 : "$2..."/ge;