18

let's say I want to return all chars after some needle char 'x' from:

$source_str = "Tuex helo babe".

Normally I would do this:

if( ($x_pos = strpos($source_str, 'x')) !== FALSE )
   $source_str = substr($source_str, $x_pos + 1);

Do you know a better/smarter (more elegant way) to do this?

Without using regexp that would not make it more elegant and probably also slower.

Unfortunately we can not do:

$source_str = substr(source_str, strpos(source_str, 'x') + 1);

Because when 'x' is not found strpos returns FALSE (and not -1 like in JS). FALSE would evaluate to zero, and 1st char would be always cut off.

Thanks,

Marco Demaio
  • 30,990
  • 33
  • 122
  • 155

5 Answers5

13

Your first approach is fine: Check whether x is contained with strpos and if so get anything after it with substr.

But you could also use strstr:

strstr($str, 'x')

But as this returns the substring beginning with x, use substr to get the part after x:

if (($tmp = strstr($str, 'x')) !== false) {
    $str = substr($tmp, 1);
}

But this is far more complicated. So use your strpos approach instead.

Gumbo
  • 594,236
  • 102
  • 740
  • 814
5

Regexes would make it a lot more elegant:

// helo babe
echo preg_replace('~.*?x~', '', $str);

// Tuex helo babe
echo preg_replace('~.*?y~', '', $str);

But you can always try this:

// helo babe
echo str_replace(substr($str, 0, strpos($str, 'x')) . 'x', '', $str);

// Tuex helo babe
echo str_replace(substr($str, 0, strpos($str, 'y')) . 'y', '', $str);
Alix Axel
  • 141,486
  • 84
  • 375
  • 483
0

I needed just this, and striving to keep it on one line for fun came up with this:

ltrim(strstr($source_str, $needle = "x") ?: $source_str, $needle);

The ternary operator was adapted in 5.3 to allow this to work.

Since PHP 5.3, it is possible to leave out the middle part of the ternary operator. Expression expr1 ?: expr3 returns expr1 if expr1 evaluates to TRUE, and expr3 otherwise.

NB. ltrim will trim multiple matching characters at the start of the string.

William George
  • 6,506
  • 3
  • 27
  • 39
0
if(strpos($source_str, 'x') !== FALSE )
   $source_str = strstr($source_str, 'x');

Less elegant, but without x in the beginning:

if(strpos($source_str, 'x') !== FALSE )
   $source_str = substr(strstr($source_str, 'x'),1);
dev-null-dweller
  • 28,330
  • 3
  • 60
  • 82
  • this will include the 'x' within $source_str though – Adam Oct 27 '10 at 17:51
  • Well thanks for your answer, but it's argueable that this is more elegant, and definitely slower "If you only want to determine if a particular needle occurs within haystack, use the faster and less memory intensive function strpos() instead." [source: http://it.php.net/strstr] – Marco Demaio Oct 27 '10 at 17:51
  • I'm confused. `strpos` is to check for substring occurence and it is used in my answer. `strstr` is to return portion of string, only if substring occurs. I find it more elegant because it does'nt need auxiliary variable, there is no misleading assignment in `if()` line and it's shorter. The only flaw of it is what @adam mentioned – dev-null-dweller Oct 27 '10 at 18:04
  • sorry, I probably did not properly explain myself, I think using a strpos+strstr is slower than using a strpos+substr. I did not test for performance (so I'm not sure, but the speed difference might be unnoticable), but beside this, it's still a two line of codes with an if (very similar to code in my question), I was hoping someone could come out with a more concise solution. – Marco Demaio Oct 28 '10 at 10:26
-1

Append a '-' at the end of $item so it always returns string before '-' even $item doesn't contain '-', because strpos by default returns the position of first occurrence of '-'.

substr($item,0,strpos($item.'-','-'))
Rajesh
  • 9,724
  • 14
  • 37
  • 58