简体   繁体   中英

Getting the first character of a string with $str[0]

I want to get the first letter of a string and I've noticed that $str[0] works great. I am just not sure whether this is 'good practice', as that notation is generally used with arrays. This feature doesn't seem to be very well documented so I'm turning to you guys to tell me if it's all right – in all respects – to use this notation?

Or should I just stick to the good ol' substr($str, 0, 1) ?

Also, I noted that curly braces ( $str{0} ) works as well. What's up with that?

Yes. Strings can be seen as character arrays, and the way to access a position of an array is to use the [] operator. Usually there's no problem at all in using $str[0] (and I'm pretty sure is much faster than the substr() method).

There is only one caveat with both methods: they will get the first byte , rather than the first character . This is important if you're using multibyte encodings (such as UTF-8). If you want to support that, use mb_substr() . Arguably, you should always assume multibyte input these days, so this is the best option, but it will be slightly slower.

The {} syntax is deprecated as of PHP 5.3.0. Square brackets are recommended.

Lets say you just want the first char from a part of $_POST, lets call it 'type'. And that $_POST['type'] is currently 'Control'. If in this case if you use $_POST['type'][0] , or substr($_POST['type'], 0, 1) you will get C back.

However, if the client side were to modify the data they send you, from type to type[] for example, and then send 'Control' and 'Test' as the data for this array, $_POST['type'][0] will now return Control rather than C whereas substr($_POST['type'], 0, 1) will simply just fail.

So yes, there may be a problem with using $str[0] , but that depends on the surrounding circumstance.

My only doubt would be how applicable this technique would be on multi-byte strings, but if that's not a consideration, then I suspect you're covered. (If in doubt, mb_substr() seems an obviously safe choice.)

However, from a big picture perspective, I have to wonder how often you need to access the 'n'th character in a string for this to be a key consideration.

It'll vary depending on resources, but you could run the script bellow and see for yourself ;)

<?php
$tests = 100000;

for ($i = 0; $i < $tests; $i++)
{
    $string = md5(rand());
    $position = rand(0, 31);

    $start1 = microtime(true);
    $char1 = $string[$position];
    $end1 = microtime(true);
    $time1[$i] = $end1 - $start1;

    $start2 = microtime(true);
    $char2 = substr($string, $position, 1);
    $end2 = microtime(true);
    $time2[$i] = $end2 - $start2;

    $start3 = microtime(true);
    $char3 = $string{$position};
    $end3 = microtime(true);
    $time3[$i] = $end3 - $start3;
}

$avg1 = array_sum($time1) / $tests;
echo 'the average float microtime using "array[]" is '. $avg1 . PHP_EOL;

$avg2 = array_sum($time2) / $tests;
echo 'the average float microtime using "substr()" is '. $avg2 . PHP_EOL;

$avg3 = array_sum($time3) / $tests;
echo 'the average float microtime using "array{}" is '. $avg3 . PHP_EOL;
?>

Some reference numbers (on an old CoreDuo machine)

$ php 1.php 
the average float microtime using "array[]" is 1.914701461792E-6
the average float microtime using "substr()" is 2.2536706924438E-6
the average float microtime using "array{}" is 1.821768283844E-6

$ php 1.php 
the average float microtime using "array[]" is 1.7251944541931E-6
the average float microtime using "substr()" is 2.0931363105774E-6
the average float microtime using "array{}" is 1.7225742340088E-6

$ php 1.php 
the average float microtime using "array[]" is 1.7293763160706E-6
the average float microtime using "substr()" is 2.1037721633911E-6
the average float microtime using "array{}" is 1.7249774932861E-6

It seems that using the [] or {} operators is more or less the same.

Speaking as a mere mortal, I would stick with $str[0] . As far as I'm concerned, it's quicker to grasp the meaning of $str[0] at a glance than substr($str, 0, 1) . This probably boils down to a matter of preference.

As far as performance goes, well, profile profile profile. :) Or you could peer into the PHP source code...

$str = 'abcdef';
echo $str[0];                 // a

In case of multibyte (unicode) strings using str[0] can cause a trouble. mb_substr() is a better solution. For example:

$first_char = mb_substr($title, 0, 1);

Some details here: Get first character of UTF-8 string

I've used that notation before as well, with no ill side effects and no misunderstandings. It makes sense -- a string is just an array of characters, after all.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM