Gonzalo.-
Gonzalo.-

Reputation: 12682

Get the last occurrence of String, as a number, and replace it

I have strings like this

Foo(2)moreFoo (1)
Foo(1)moreFoo (2)
Foo(99)moreFoo (3)
Foo(99)moreFoo (9)
Foo

I need to take each string, and change the last (number)

So, in this case, I would like to get for each string:

Foo(2)moreFoo (2)
Foo(1)moreFoo (3)
Foo(99)moreFoo (4)
Foo(99)moreFoo (10)
Foo(1)

It would be like get the string, get the last occurence of (number), and replace it by (number +1)

How can I do this?

I've checked this answer, but not sure how to change it.

I've started with

$subject = 'Foo (2)(1)';

if(preg_match('\([0-9]+\)', $subject))
{   
    $pos = strrpos($subject, '\([0-9]+\)');

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

but the problem is that could be that the number will be (10) so, I cannot just get the last 3 characters.

The (number), if exists, will be at end. It could be at middle, but the interesting one is in the end.

Upvotes: 0

Views: 159

Answers (2)

Ja͢ck
Ja͢ck

Reputation: 173642

You can use preg_replace_callback() to target the individual matches and replace them:

echo preg_replace_callback('/\((\d+)\)$/m', function($match) {
    return '(' . ++$match[1] . ')';
}, $subject);

The pattern matches a parenthesized number at the end of each line and calls the anonymous function to perform the replacement. It uses $ combined with the /m modifier to match the end of each line.

Matching lines that don't have any (number) you need a somewhat trickier expression:

echo preg_replace_callback('/(?:\((\d+)\)|([^)]))$/m', function($match) {
    return isset($match[2]) ? "{$match[2]}(1)" : '(' . ++$match[1] . ')';
}, $subject);

The alternation matches either a (number) or something that's not a ) at the end of the line. If the line didn't end with ) we should add (1).

Upvotes: 1

Chris Rasco
Chris Rasco

Reputation: 2731

You'll use preg_match_all() instead of preg_match() since we want the last match. This will get you ready to use a function like you mentioned, but you'll still need to strip the parens and add 1.

$subject = 'Foo (2)(1)';

echo $subject,"<br />";

if(preg_match_all('/\([0-9]+\)/', $subject, $matches))
{   
    $last_match =  $matches[0][count($matches[0])-1];
    $pos = strrpos($subject, $last_match);

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

Upvotes: 0

Related Questions