PHP文字列内の文字列の最後の出現を置き換えますか?


回答:


228

この関数を使用できます。

function str_lreplace($search, $replace, $subject)
{
    $pos = strrpos($subject, $search);

    if($pos !== false)
    {
        $subject = substr_replace($subject, $replace, $pos, strlen($search));
    }

    return $subject;
}

何があっても、これはまだtrueを返していました。次のように変更することを検討してください:if($ pos){$ subject = substr_replace($ subject、$ replace、$ pos、strlen($ search)); $ subjectを返す; } else {falseを返す; }
2013

4
@ジェイソン何があっても返ってこないTRUE。何があっても文字列を返します。交換ができない場合は、元のを返す$subjectだけのようにsubstr_replace してstr_replaceください。
Mischa 2013

@Mischaこの場合も同じではないですか?!str_lreplaceのようなことを試みていましたが、falseが返されない場合、trueと見なされますよね?いずれにせよ、これは私を助けてくれて感謝しています。ありがとう。
Jazzy 2013

1
これはどのように機能しますか?strpos — Find the position of the first occurrence of a substring in a string-編集:すごい。PHPの天才は本当にと呼ばれる関数作られたstrposとはstrrpos?ありがとう....
BarryBones41

1
@BarryこれはPHPが非難に値しないもの場合:-)名は数十年前の上にパターン化されているstrstrstrrstr標準Cライブラリの、同じ機能です。(しかし、名前を変更する必要がありましたか?)
アレクシス

30

別の1ライナー、ただしpregなし:

$subject = 'bourbon, scotch, beer';
$search = ',';
$replace = ', and';

echo strrev(implode(strrev($replace), explode(strrev($search), strrev($subject), 2))); //output: bourbon, scotch, and beer

3
FWIW、承認されたソリューションは、このソリューションより約35%高速です。
JustCarty 2017年

27
$string = 'this is my world, not my world';
$find = 'world';
$replace = 'farm';
$result = preg_replace(strrev("/$find/"),strrev($replace),strrev($string),1);
echo strrev($result); //output: this is my world, not my farm

私の意見では最もクールなソリューションであり、それでも理解するのは簡単です。
Blackbam 2018

なぜすべての文字列を逆にしても機能するのですか?正規表現を使用すると、特定のパフォーマンス向上が(あると思います)ありますか?
カマフェザー

いいえ、それは実際にはパフォーマンスを低下させますが、それは最後のオカレンスのみが必要なので、検索を1つに制限し、最初に必要な場合はすべて逆にする必要があるためです
Tofandel

15

次のかなりコンパクトなソリューションは、PCREポジティブ先読みアサーションを使用して、対象のサブストリングの最後の出現、つまり、同じサブストリングの他の出現が続かないサブストリングの出現と一致します。したがって、例ではをに置き換えてlast 'fox''dog'ます。

$string = 'The quick brown fox, fox, fox jumps over the lazy fox!!!';
echo preg_replace('/(fox(?!.*fox))/', 'dog', $string);

出力: 

The quick brown fox, fox, fox jumps over the lazy dog!!!

5
アイデアは良いですが、コードはそうではありません。それは:$string = 'The quick brown fox, fox, fox jumps over the lazy fox!!!'; echo preg_replace('/(fox(?!.*fox))/', 'dog', $string);
Roemer

確かに、私が投稿したコードは、最後のものを除いて「fox」のすべてのインスタンスを「dog」に変更しますが、私たちが望むのは正反対です。?=を?に置き換えることを指摘していただきありがとうございます。問題を修正します。
John Sonderson、2015

11

あなたはこれを行うことができます:

$str = 'Hello world';
$str = rtrim($str, 'world') . 'John';

結果は「ハロージョン」です。

よろしく


4
これは、繰り返される文字がない限り機能します。私の状況では、アーカイブ日付からページ番号を取り除いているので、「2015-12 / 2」があり、すべての/および2つすべてが「2015-1」になります。
Mike

これは、検索された最後の出現が最後の単語であり、その後に追加の文字がない場合にのみ機能します。
AwesomeGuy

これはrtrimあなたが考えているように振る舞わないので機能しません。検索文字列に存在するすべての文字を任意の順序で削除します(常に置換を追加します)。たとえば、「He​​llo word」->「Hello John」、「Hello lord」->「Hello John」、「Helloモーター」->「Hello motJohn」、「Hello worldy」->「Hello worldyJohn」。
Jake

5

これも機能します:

function str_lreplace($search, $replace, $subject)
{
    return preg_replace('~(.*)' . preg_quote($search, '~') . '(.*?)~', '$1' . $replace . '$2', $subject, 1);
}

更新少し簡潔なバージョン(http://ideone.com/B8i4o):

function str_lreplace($search, $replace, $subject)
{
    return preg_replace('~(.*)' . preg_quote($search, '~') . '~', '$1' . $replace, $subject, 1);
}

私はそれを間違っていますか?その場合は無視してください:) ||| echo str_lreplace( "x"、 "y"、 "this x or that x"); =>出力: "y"参照:ideone.com/UXuTo
edorian

@edorian:おっと!申し訳ありませんが、私は急いでそれを投稿しました、正しいバージョンはここにあります:ideone.com/vR073
Alix Axel

5

たった1行のコード(後の答えですが、追加する価値があります):

$string = 'The quick brown fox jumps over the lazy dog';
$find_me = 'dog';

preg_replace('/'. $find_me .'$/', '', $string);

末尾の$は文字列の終わりを示します。


5

これは古代の質問ですが、なぜ誰もが最も単純な正規表現ベースのソリューションを見落としているのですか?通常の正規表現の数量詞は貪欲です、人々!パターンの最後のインスタンスを見つけたい場合は、その.*前にくっついてください。方法は次のとおりです。

$text = "The quick brown fox, fox, fox, fox, jumps over etc.";
$fixed = preg_replace("((.*)fox)", "$1DUCK", $text);
print($fixed);

これは、 "fox"の最後のインスタンスを、本来のように "DUCK"に置き換えて出力します。

The quick brown fox, fox, fox, DUCK, jumps over etc.

1
ありがとう!これを実現するために私の表現をラップするのに最適な関数です。私の場合、最後のカンマを「および」で置き換えています。この回答リストを少し下にスクロールしてよかったです。
rlhane

3
$string = "picture_0007_value";
$findChar =strrpos($string,"_");
if($findChar !== FALSE) {
  $string[$findChar]=".";
}

echo $string;

コードの誤りは別として、Faruk Unalは最高のアンサーを持っています。1つの関数がトリックを行います。


$ findCharがfalseでないかどうかを確認する必要があります(承認された回答と同じ方法)。文字列に検索文字列が含まれていない場合は、通知が表示され、最初の文字が置き換えられます。
ぎくしゃくした

これはすばらしいですが、現状では1文字を1文字に置き換えることしかできません。
ピート

3

strrpos()を使用して、最後の一致を見つけることができます。

$string = "picture_0007_value";
$findChar =strrpos($string,"_");

$string[$findChar]=".";

echo $string;

出力:picture_0007.value


2

受け入れられた回答の省略形

function str_lreplace($search, $replace, $subject){ 
    return is_numeric($pos=strrpos($subject,$search))?
    substr_replace($subject,$replace,$pos,strlen($search)):$subject;
}


0

reg式で「$」を使用して、文字列の末尾と一致させます

$string = 'The quick brown fox jumps over the lazy fox';
echo preg_replace('/fox$/', 'dog', $string);

//output
'The quick brown fox jumps over the lazy dog'

4
これは、最後の出現が文字列ideone.com/nbNSNq
cawecoy

1
最後の 'fox'の後に他の文字が表示される場合、これは機能しません。
John Sonderson、2015年

0

興味のある方:regexを使用して右側から置換できるようにpreg_matchを利用する関数を書きました。

function preg_rreplace($search, $replace, $subject) {
    preg_match_all($search, $subject, $matches, PREG_SET_ORDER);
    $lastMatch = end($matches);

    if ($lastMatch && false !== $pos = strrpos($subject, $lastMatchedStr = $lastMatch[0])) {
        $subject = substr_replace($subject, $replace, $pos, strlen($lastMatchedStr));
    }

    return $subject;
}

または、両方のオプションの簡単な組み合わせ/実装として:

function str_rreplace($search, $replace, $subject) {
    return (false !== $pos = strrpos($subject, $search)) ?
        substr_replace($subject, $replace, $pos, strlen($search)) : $subject;
}
function preg_rreplace($search, $replace, $subject) {
    preg_match_all($search, $subject, $matches, PREG_SET_ORDER);
    return ($lastMatch = end($matches)) ? str_rreplace($lastMatch[0], $replace, $subject) : $subject;
}

https://stackoverflow.com/a/3835653/3017716およびhttps://stackoverflow.com/a/23343396/3017716に基づく

弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.