preg_replace все вхождения в строке с определенными разделителями

Я пытаюсь заменить все вхождения « a » на « b » внутри некоторой строки. Проблема в том, что мне нужно заменить только те буквы, которые находятся внутри скобок:

asd asd asd [asd asd asd] asd asd asd

На данный момент у меня есть этот код:

$what = '/(?<=\[)a(?=.*?\])/s'; $with = 'b'; $where = 'asd asd asd [asd asd asd] asd asd asd'; 

Но он заменяет только первый «а», и я получаю этот результат:

asd asd asd [bsd asd asd] asd asd asd

Я действительно должен сделать это только с одним вызовом preg_replace.

Вы не можете сделать это с помощью одного вызова preg_replace потому что lookbehind должен будет сказать «есть квадратная скобка открытия где-то перед матчем», и это невозможно, так как шаблоны lookbehind должны иметь фиксированную длину.

Зачем вам это нужно в любом случае? Это можно сделать довольно легко с помощью preg_replace_callback , где вы бы соответствовали группам содержимого внутри квадратных скобок и каждый раз использовали preg_replace в матче (или просто просто str_replace если все, что вы собираетесь делать, это заменить «a» на «b»).

Пример:

 $what = '/\[([^]]*)\]/'; $where = 'asd asd asd [asd asd asd] asd asd asd'; echo preg_replace_callback( $what, function($match) { return '['.str_replace('a', 'b', $match[1]).']'; }, $where); 

Попробуйте это (это то, что точно объяснил Джон)

 function replace_a_with_b($matches) { return str_replace("a", "b", $matches[0]); } $text = 'asd asd asd [asd asd asd] asd asd asd'; echo preg_replace_callback("#(\[[^]]+\])#", "replace_a_with_b", $text); 

Вывод:

 asd asd asd [bsd bsd bsd] asd asd asd