2010-09-30 2 views
1

Это то, что я мог взломать вместе, но я задавался вопросом, было ли у кого-то чистое решение моей проблемы. Что-то, что я бросаю вместе, не обязательно будет очень кратким или быстрым!Обрезать только первое и последнее вхождение символа в строке (PHP)

У меня есть такая строка ///hello/world///. Мне нужно снять только первый и последний слэш, ни один из остальных, так что я получаю строку, подобную этой //hello/world//.

PHP trim не совсем прав: выполнение trim($string, '/') вернет hello/world.

Следует отметить, что в начале или конце строки не обязательно будет никаких косых черт. Вот несколько примеров того, что я хотел бы произойти с разными строками:

///hello/world/// > //hello/world// 
/hello/world/// > hello/world// 
hello/world/ > hello/world 

Заранее благодарим за любую помощь!

+0

Почему бы не привести реальный пример вместо такой манекен? Может быть, может быть лучшее решение, только для вашего случая? Реальный случай. –

+0

@col Это почти реальный мир. Это часть класса маршрутизации, который передает текущий путь URL-адреса для перехода к соответствующему контроллеру. Я просто заметил, что 'http: // example.com/path/to/file' разрешается для того же контроллера, что и' http: //example.com /// path/to/file // ', поэтому приведенный выше пример почти точно, что строки, которые я получаю, будут выглядеть так: :) Я обрабатываю пути – Rowan

+0

Но в чем причина наличия таких кратных косых черт? Пути нужны только одному. Я никогда не видел путь, подобный этому: /// path/to/file // '. Где вы их получите, и почему вы не хотите нормализовать, что делает его обычным/path/to/file /? –

ответ

8

Первое, на мой взгляд:

if ($string[0] == '/') $string = substr($string,1); 
if ($string[strlen($string)-1] == '/') $string = substr($string,0,strlen($string)-1); 
+1

Я считаю, что метод подстроки, вероятно, будет работать намного быстрее, чем регулярное выражение. – Kevin

+0

Это очень грубо говоря, что я бы бросил вместе. Я бы хотел избежать регулярного выражения, если он будет медленнее, есть ли какая-либо статистика для резервного копирования скорости простых функций манипуляции строками vs regex? – Rowan

+3

@ Роуэн: нет, таких статистических данных нет, так как это зависит от фактических манипуляций, иногда регулярные выражения действительно выигрывают.Единственный способ рассказать - сравнить его с ожидаемыми строками, и даже тогда я бы сказал, что использование одного над другим на основе производительности - это, вероятно, микрооптимизация. – Wrikken

0

Я думаю, что это то, что вы вы ищете:

preg_replace('/\/(\/*[^\/]*?\/*)\//', '\1', $text); 
+2

Арг, разве вы не можете просто переключать разделители? '#/(/ * [^ /] *?/*)/#'. Однако вы забудете его привязать: '# ^/(/ * [^ /] *?/*) $/#', И для эффективности вы также можете использовать 'preg_replace ('# (^/|/$) # ',' ', $ text); ' – Wrikken

+3

Разница между'/\/(\/* [^ \ /] *? \/*) \ // 'и' # (^/|/$) # ' поэтому люди быстро записывают регулярное выражение как нечитаемое. –

0

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

preg_replace('/^(\/?)(.*)\1$/','\2',$text); 

Это имеет то преимущество, что, если вы хотите использовать символы, отличные от /, вы можете сделать это более разборчиво. Он также заставляет символ/начинать и заканчивать строку и разрешать/появляться внутри строки. Наконец, он только удаляет символ с самого начала, если в конце есть символ, и наоборот.

0

Еще одна реализация:

function otrim($str, $charlist) 
{ 
return preg_replace(sprintf('~^%s|%s$~', preg_quote($charlist, '~')), '', $str); 
} 
+0

Это дало мне 'Fatal error: Uncaught ErrorException: sprintf(): Слишком мало аргументов' –

0

Это было больше, чем 6 лет назад, но я даю может ответить так или иначе:

function trimOnce($value) 
{ 
    $offset = 0; 
    $length = null; 
    if(mb_substr($value,0,1) === '/') { 
     $offset = 1; 
    } 
    if(mb_substr($value,-1) === '/') { 
     $length = -1; 
    } 
    return mb_substr($value,$offset,$length); 
} 
Смежные вопросы