FAQ
Hello everyone,

I would like to open the discussion around the support of negative indexes, as I feel a lot of developers will benefit from this syntactical sugar.

Example:
$foo = array(1,2,3);
echo $foo[2]; // 3
echo $foo[-1]; // 3

$bar = 'baz';
echo $foo[2]; // 'z'
echo $foo[-1]; // 'z'

The change to PHP is quite trivial, but as it's a change to language it needs to be discussed.

I'm happy to open a RFC, I have got a wiki account but I haven't got permission to add a wiki page. Whom do I need to contact regarding getting correct permissions to add/edit wiki pages?

Kind Regards
Marc

Search Discussions

  • Matthew Fonda at Jan 14, 2011 at 6:33 pm

    On Fri, Jan 14, 2011 at 10:21 AM, Marc Easen wrote:
    Hello everyone,

    I would like to open the discussion around the support of negative indexes, as I feel a lot of developers will benefit from this syntactical sugar.
    It would be convenient, but PHP already allows arrays to have negative
    indices. Changing their behavior would be a major BC break.

    Best Regards,
    --Matthew
  • Marcin Babij at Jan 14, 2011 at 6:35 pm

    Hello everyone,

    I would like to open the discussion around the support of negative indexes, as I feel a lot of developers will benefit from this syntactical sugar.

    Example:

    echo $foo[2]; // 3
    echo $foo[-1]; // 3
    Negative indexes are used already - for negative indexes.
    What should:

    $foo = array(1,2,3, -1 => 4, 5, 6);
    echo $foo[-1];

    return? Now it returns 4.
    $bar = 'baz';
    echo $foo[2]; // 'z'
    echo $foo[-1]; // 'z'

    The change to PHP is quite trivial, but as it's a change to language it needs to be discussed.

    I'm happy to open a RFC, I have got a wiki account but I haven't got permission to add a wiki page. Whom do I need to contact regarding getting correct permissions to add/edit wiki pages?
  • Stas Malyshev at Jan 14, 2011 at 6:47 pm
    Hi!
    I would like to open the discussion around the support of negative
    indexes, as I feel a lot of developers will benefit from this
    syntactical sugar.
    What you are looking for is implemented in array_slice(). Python has
    shortcuts for this thing, like a[1:-1], but PHP doesn't. If you wanted
    to RFC something here, I think the idea of $a[X:Y] with array_slice
    semantics could be doable. $a[-1:1] would be your case then.
    --
    Stanislav Malyshev, Software Architect
    SugarCRM: http://www.sugarcrm.com/
    (408)454-6900 ext. 227
  • Marc Easen at Jun 4, 2012 at 7:09 pm
    I have submitted a patch to support negative indexs in strings, as per
    the conversation adding them to arrays could possibly detract from the
    syntactical sugar they are indented to be.

    In summary:

    An alternative to:
    $var = 'abc';
    echo $var[strlen($var) - 1];

    Can be:
    $var = 'abc';
    echo $var[-1];

    Commit:
    https://github.com/Easen/php-src/commit/7016e52677f525139491467f3e76862b9a597b76

    Pull request:
    https://github.com/php/php-src/pull/100

    Thanks,

    On 14/01/11 18:47, Stas Malyshev wrote:
    Hi!
    I would like to open the discussion around the support of negative
    indexes, as I feel a lot of developers will benefit from this
    syntactical sugar.
    What you are looking for is implemented in array_slice(). Python has
    shortcuts for this thing, like a[1:-1], but PHP doesn't. If you wanted
    to RFC something here, I think the idea of $a[X:Y] with array_slice
    semantics could be doable. $a[-1:1] would be your case then.
  • Richard Lynch at Jun 11, 2012 at 6:32 pm

    On Mon, June 4, 2012 2:08 pm, Marc Easen wrote:
    I have submitted a patch to support negative indexs in strings, as per
    the conversation adding them to arrays could possibly detract from the
    syntactical sugar they are indented to be.

    In summary:

    An alternative to:
    $var = 'abc';
    echo $var[strlen($var) - 1];

    Can be:
    $var = 'abc';
    echo $var[-1];
    This seems simple enough for a hard-coded -1, but...

    Would $var[-2] be strlen($var) - 2 and so on?

    And then one would expect some rather complex logic to compute -N for
    $var[-N]

    At that point, this becomes a pretty big WTF, imho.

    I've never honestly felt it to be a big burden to use strlen($var) -
    1, so I don't really see the point, at least for me.
  • Stas Malyshev at Jun 11, 2012 at 7:13 pm
    Hi!
    Can be:
    $var = 'abc';
    echo $var[-1];
    This seems simple enough for a hard-coded -1, but...

    Would $var[-2] be strlen($var) - 2 and so on?
    The main question is what happens with "foo"[-4] or ['x'][-2].
    And then one would expect some rather complex logic to compute -N for
    $var[-N]
    I don't see much of complex logic here, but $a[2] = 'a' would create a
    new array element if it does not exist, while $a[-2] can't. Not a big
    issue, but somewhat inconsistent I guess.

    --
    Stanislav Malyshev, Software Architect
    SugarCRM: http://www.sugarcrm.com/
    (408)454-6900 ext. 227
  • Richard Lynch at Jun 11, 2012 at 7:26 pm

    On Mon, June 11, 2012 2:13 pm, Stas Malyshev wrote:
    And then one would expect some rather complex logic to compute -N
    for
    $var[-N]
    I don't see much of complex logic here, but $a[2] = 'a' would create a
    new array element if it does not exist, while $a[-2] can't. Not a big
    issue, but somewhat inconsistent I guess.
    $n = some_incredibly_long_and_complex_computation();
    //and, for real fun, sometimes it returns positive, and sometimes
    negative.

    $s = $var[$n];

    //a few hundred lines later, buried somewhere else

    if ($n < 0){
    //whatever
    }
    else{
    //something entirely different
    }

    Sooner or later, somebody will do that, and I really don't want to
    have to un-tangle all that mess to figure out if $n is positive or
    negative for the sake of saving a few keystrokes...
  • Marc Easen at Jun 11, 2012 at 8:25 pm

    On 11/06/12 20:28, Richard Lynch wrote:
    On Mon, June 11, 2012 2:13 pm, Stas Malyshev wrote:
    And then one would expect some rather complex logic to compute -N
    for
    $var[-N]
    I don't see much of complex logic here, but $a[2] = 'a' would create a
    new array element if it does not exist, while $a[-2] can't. Not a big
    issue, but somewhat inconsistent I guess.
    $n = some_incredibly_long_and_complex_computation();
    //and, for real fun, sometimes it returns positive, and sometimes
    negative.

    $s = $var[$n];
    If $n is a negative value, an E_NOTICE will be triggered. To not do
    if ($n< 0){
    //whatever
    }
    else{
    //something entirely different
    }
    Prior to your string offset can be looked at being bad practice.
  • Galen Wright-Watson at Jun 11, 2012 at 7:29 pm

    On Mon, Jun 11, 2012 at 12:13 PM, Stas Malyshev wrote:

    Hi!
    Can be:
    $var = 'abc';
    echo $var[-1];
    This seems simple enough for a hard-coded -1, but...

    Would $var[-2] be strlen($var) - 2 and so on?
    The main question is what happens with "foo"[-4] or ['x'][-2].
    The same thing that currently happens for:

    $f='foo'; echo $f[strlen($f)-4];
    $a=['x']; $a[count($a)-2];

    which appears to be notices:

    Notice: Uninitialized string offset: -1 in - on line 2
    Notice: Undefined offset: -1 in - on line 3
    And then one would expect some rather complex logic to compute -N for
    $var[-N]
    I don't see much of complex logic here, but $a[2] = 'a' would create a
    new array element if it does not exist, while $a[-2] can't. Not a big
    issue, but somewhat inconsistent I guess.
    Negative indices are currently valid for arrays. If anyone makes use of
    negative indices, this could break their script. Personally, I'd rather
    have Marc Easen's behavior.
  • Marc Easen at Jun 11, 2012 at 9:01 pm

    On 11/06/12 20:13, Stas Malyshev wrote:
    Hi!
    Can be:
    $var = 'abc';
    echo $var[-1];
    This seems simple enough for a hard-coded -1, but...

    Would $var[-2] be strlen($var) - 2 and so on?
    The main question is what happens with "foo"[-4] or ['x'][-2].
    And then one would expect some rather complex logic to compute -N for
    $var[-N]
    I don't see much of complex logic here, but $a[2] = 'a' would create a
    new array element if it does not exist, while $a[-2] can't. Not a big
    issue, but somewhat inconsistent I guess.
    Please note I'm not referring the negative indexes in arrays, just
    strings. As I see strings as being simpler to implement and produce a
    greater benefit compared to supporting negative indexes for arrays. As
    arrays are more complex structures and adding this behaviour would
    complicate things somewhat.
  • Marc Easen at Jun 17, 2012 at 7:53 pm
    Hi Lars,

    I don't think there needs to be a new operator, as it is possible to
    achieve this behaviour without adding a new language construct. The odd
    thing with PHP as I'm sure you are aware of is that arrays can be either
    a lists or a dictionary. This is where this becomes quite difficult to
    implement:

    Numerical keyed array:

    $a = array('foo', 'bar', 'baz');
    $a[0] === 'foo'

    I would expect:

    $a[-1] === 'baz';

    An string keyed array:

    $b = array('foo' => 1, 'bar' => 2, 'baz' => 3);
    $b[0] === 1;

    Would generate an E_NOTICE: PHP Notice: Undefined offset: 0 in php
    shell code on line 1.
    An negative offset would also generate the same E_NOTICE.

    So going back to your point, the change would only be to numeric based
    arrays (list) and strings. It could be possible to string keyed arrays
    to be accessed by the numeric counter parts, but I'm not familiar to
    comment on if this is even possible.


    It seems this topic has generated a lot of interest, I feel the best way
    to proceed would be to write a RFC. I've never written one before so
    could someone give me access to create a page on the RFC site or create
    a RFC for me and give me permission to update it, my username is 'easen'.

    Thanks,
    Marc

    On 17/06/12 15:14, Lars Strojny wrote:
    Hi Marc,

    Am 11.06.2012 um 23:01 schrieb Marc Easen:

    [...]
    I don't see much of complex logic here, but $a[2] = 'a' would create a
    new array element if it does not exist, while $a[-2] can't. Not a big
    issue, but somewhat inconsistent I guess.
    Please note I'm not referring the negative indexes in arrays, just strings. As I see strings as being simpler to implement and produce a greater benefit compared to supporting negative indexes for arrays. As arrays are more complex structures and adding this behaviour would complicate things somewhat.
    I would propose not to try implementing a different behavior for strings than it is for arrays. I think we need a more convenient way to access parts of a string/parts of an array than substr() and array_slice() provide. But this will most likely be a new operator.

    cu,
    Lars
  • Lars Strojny at Jun 17, 2012 at 10:53 pm
    Hi Marc,


    Am 17.06.2012 um 21:53 schrieb Marc Easen:
    [...]
    Numerical keyed array:

    $a = array('foo', 'bar', 'baz');
    $a[0] === 'foo'

    I would expect:

    $a[-1] === 'baz';

    An string keyed array:

    $b = array('foo' => 1, 'bar' => 2, 'baz' => 3);
    $b[0] === 1;

    Would generate an E_NOTICE: PHP Notice: Undefined offset: 0 in php shell code on line 1.
    An negative offset would also generate the same E_NOTICE.

    So going back to your point, the change would only be to numeric based arrays (list) and strings. It could be possible to string keyed arrays to be accessed by the numeric counter parts, but I'm not familiar to comment on if this is even possible.
    I see, must have overread that. This makes it slightly better but not optimal, as too varying behavior for hashes vs. lists will be harder to explain. We could go down that road and separate the both more and more but given the history (and the usage patterns) of arrays in PHP I'm not convinced this is a good idea.

    I would prefer something like this (and no, I don't propose using ':' as an operator for real):

    $string = "bar";
    $string:-1 // "b"
    $string:-2 // "r"
    $string:-10 // NULL

    $list = array("one", "two", "three");
    $list:-1 // "three"
    $list:-2 // "two"
    $list:-10 // NULL

    $hash = array("one" => 1, "two" => 2, "three" => 3)
    $hash:-1 // 3
    $hash:-2 // 2
    $hash:-10 // 10

    As using arrays as hashes let’s them behave in a FIFO kind of way, we can do proper slicing.
    It seems this topic has generated a lot of interest, I feel the best way to proceed would be to write a RFC. I've never written one before so could someone give me access to create a page on the RFC site or create a RFC for me and give me permission to update it, my username is 'easen'.
    For sure, RFC makes sense. I like the general idea, I’m just not sure about the syntax.

    cu,
    Lars
  • Slevy1 at Jun 12, 2012 at 11:21 pm
    I feel that for PHP to incorporate some of the convenience that Python offers is a good particularly with respect to attracting the upcoming generation. PHP needs an injection of new coolness to attract and captivate the imagination of young college-age people who are being exposed to Python as part of their CS curriculum.

    I think Easen's proposal for PHP to have negative indexing for strings (not arrays) is well-thought out, and conservative too. I think it would be an excellent addition.

    +1!

    Sincerely,
    Sharon

Related Discussions

Discussion Navigation
viewthread | post
Discussion Overview
groupphp-internals @
categoriesphp
postedJan 14, '11 at 6:21p
activeJun 17, '12 at 10:53p
posts14
users8
websitephp.net

People

Translate

site design / logo © 2022 Grokbase