将数字和运算符添加到数组PHP

时间:2018-01-26 19:45:52

标签: php

我试图在数组中添加一行数字和运算符。我怎么能正确地做到这一点?

我希望将每个数字组分隔为一个索引和下一个索引运算符。

我需要你的帮助来告诉我代码中的错误在哪里:

function toArray($s){

    $le = strlen($s);
    $j = 0;
    $ordered_numbers_operators = array();
    $operators = array('+','-','*','/','%','(',')');

    for ( $i=0;$i<$le;$i++ ){

        if ( in_array( $s[$i], $operators )  ) {
            $ordered_numbers_operators[$j] = $s[$i];
            $j++;

        } else {

            if ( $i+1 == $le ){
                $ordered_numbers_operators[$j] = $s[$i];

            } else {

                if ( $s[$i+1] !== in_array( $s[$i+1], $operators ))  {

                    if ( $s[$i+1] == in_array( $s[$i+1], $operators )){
                        echo "\$i = " . $i . "<br />" ;
                        $ordered_numbers_operators[$j]=$s[$i];
                        $j++;

                    } else {

                        $ordered_numbers_operators[$j] = $s[$i] . $s[$i+1];
                        $i++; $j++;
                    }

                }
            }
        }
    }

    return $ordered_numbers_operators;

    }

$string = '6+4*4+100+444*6*13*14';

$arr = toArray($string);

预期结果:

[0] => 6
[1] => +
[2] => 4
[3] => *
[4] => 4
[5] => +
[6] => 100
[7] => +  
[8] => 444  
[9] => *
[10] => 6
[11] => *
[12] => 13
[13] => *
[14] => 14    

实际结果:

[0] => 6
[1] => +
[2] => 4
[3] => *
[4] => 4
[5] => +
[6] => 1
[7] => 0
[8] => 0
[9] => +
[10] => 44
[11] => 4
[12] => *
[13] => 6
[14] => *
[15] => 13
[16] => *
[17] => 14

3 个答案:

答案 0 :(得分:5)

如果没有正则表达式,您可以更简单地完成此操作。见this example, to test and run

<?php


function toArray($s){
    $operators = array('+','-','*','/','%','(',')');

    $finalArr = [];
    $curStr = '';
    foreach (str_split($s) as $char) {
        if (in_array($char, $operators)) {
            //Alright, we have an operator. Append the entire number
            $finalArr[] = $curStr;
            //And also the operator
            $finalArr[] = $char;
            //Reset the current string back to empty
            $curStr = '';
        } else {
            //Not an operator? Just keep appending the current number
            $curStr .= $char;
        }
    }

    //Add final leftover string
    if ($curStr !== '') { //Sanity check here (This shouldn't ever be empty, as you wouldn't end with an operator)
        $finalArr[] = $curStr;
    }

    //Return
    return $finalArr;
}

$string = '6+4*4+100+444*6*13*14';

$arr = toArray($string);

print_r($arr);

答案 1 :(得分:4)

您可以使用正则表达式和preg_split来完成,更容易一些。

$parts = preg_split('~([+*/-])~', '6+4*4+100+444*6*13*14', -1, PREG_SPLIT_DELIM_CAPTURE | PREG_SPLIT_NO_EMPTY);
print_r($parts);

演示:https://3v4l.org/oCrLG

请注意-,因为字符类中的最后一个字符很重要。如果在此之后添加更多字符,-将在每边最近的字符之间创建一个范围。您要分隔的任何字符都可以添加到[]中。如果添加],请务必将其转义,以便闭包正确。您可以在此处阅读有关角色类的更多信息,https://www.regular-expressions.info/charclass.html

字符类也可以使它不需要转义特殊的正则表达式字符。您也可以像这样删除字符类。

$parts = preg_split('~(\+|\*|/|-)~', '6+4*4+100+444*6*13*14', -1, PREG_SPLIT_DELIM_CAPTURE | PREG_SPLIT_NO_EMPTY);
print_r($parts);

演示:https://3v4l.org/Jha6P

此外,在运算符之前和之后,\s*\h*可以选择空格。

$parts = preg_split('~\h*([+*/-])\h*~', '6+4*4+100+444*6*13*14', -1, PREG_SPLIT_DELIM_CAPTURE | PREG_SPLIT_NO_EMPTY);
print_r($parts);

答案 2 :(得分:1)

另一种无正则表达式的方法是使用array_reduce

您可以使用str_split将字符串拆分为数组,然后使用array_reduce构建所需的数组(以便连接连续的数字)。让我们一步一步来做。首先,使用array_reduce中的简单回调函数,我们得到与str_split相同的结果:

function toArray($string) {
    $chars = str_split($string);

    return array_reduce($chars, function($result, $current) {
        $result[] = $current;

        return $result;
    }, []);
}

$input = '6+4*4+100+444*6*13*14';
print_r(toArray($input));

/*
Array
(
    [0] => 6
    [1] => +
    [2] => 4
    [3] => *
    [4] => 4
    [5] => +
    [6] => 1
    [7] => 0
    [8] => 0
    [9] => +
    [10] => 4
    [11] => 4
    [12] => 4
    [13] => *
    [14] => 6
    [15] => *
    [16] => 1
    [17] => 3
    [18] => *
    [19] => 1
    [20] => 4
)
*/

下一步是在迭代array_reduce中的字符时检查先前的值和当前值。如果它们都是数字,我们想加入它们:

function toArray($string) {
    $chars = str_split($string);

    return array_reduce($chars, function($result, $current) {
        $previous = $result[] = array_pop($result);

        if (is_numeric($previous) && is_numeric($current)) {
            $result[] = array_pop($result) . $current;
        } else {
            $result[] = $current;
        }

        return $result;
    }, []);
}

$input = '6+4*4+100+444*6*13*14';
print_r(toArray($input));

/*
Array
(
    [0] =>
    [1] => 6
    [2] => +
    [3] => 4
    [4] => *
    [5] => 4
    [6] => +
    [7] => 100
    [8] => +
    [9] => 444
    [10] => *
    [11] => 6
    [12] => *
    [13] => 13
    [14] => *
    [15] => 14
)
*/

几乎就在那里!该数组在索引零处包含一个额外元素。 (这是因为我们使用$previous = $result[] = array_pop($result);获取上一项。其值为null,因为最初$result是一个空数组,因此array_pop返回null。我们可以摆脱额外的元素,例如与array_slice

function toArray($string) {
    $chars = str_split($string);

    $array = array_reduce($chars, function($result, $current) {
        $previous = $result[] = array_pop($result);

        if (is_numeric($previous) && is_numeric($current)) {
            $result[] = array_pop($result) . $current;
        } else {
            $result[] = $current;
        }

        return $result;
    }, []);

    return array_slice($array, 1);
}

$input = '6+4*4+100+444*6*13*14';
print_r(toArray($input));

/*
Array
(
    [0] => 6
    [1] => +
    [2] => 4
    [3] => *
    [4] => 4
    [5] => +
    [6] => 100
    [7] => +
    [8] => 444
    [9] => *
    [10] => 6
    [11] => *
    [12] => 13
    [13] => *
    [14] => 14
)
*/

演示:https://3v4l.org/qZsvs