将输入文本解析为数组和求和值

Parsing input text to array and sum values

你好:)我正在开发我的迷你应用程序。我有以下文本,从第 3 方网页复制:

Type A    GZ 600    11.09.2021 12:00        OST    9
Type A    GZ 601    11.09.2021 13:20        ADS    1
Type A    GZ 602    11.09.2021 21:35        OCS    1
Type A    GZ 603    11.09.2021 14:50        CSE    10
Type B    GZ 600    11.09.2021 12:00        OST    5
Type B    GZ 601    11.09.2021 13:20        ADS    3
Type B    GZ 602    11.09.2021 21:35        OCS    6
Type B    GZ 603    11.09.2021 14:50        CSE    12

我需要将其解析为以下格式: $s = 10, $ns = 11, $bs = 26,喜欢:

echo "S:" . $s . " NS:" . $ns . " BS:" . $bs; // Output: S:10 NS:11 BS:26

where:
$fa = array("OCS", "CSE"); is array of codes
$ns is sum of Type A last column numbers, which 5 column 3-letter code is in the array, 
$s is sum of Type A last column numbers, which 5 column 3-letter code is not in the array
$bs is just sum of Type B last column numbers

我现在的代码如下:

if(!empty($_POST['indata'])){
  $in_data = $_POST['indata'];                // Get POST data
  $fa = array("OCS", "CSE");                  // Make array
  $ns = 0;                                    // Init ns value
  $s = 0;                                  // Init ss value
  foreach(explode("/n",$in_data) as $line){   // Divide text to lines
    $info[] = explode("    ", $line);         // Divide line to values and put them to array 
    print_r($info);  //Show input for test purposes                         
    if(in_array($info[4], $fa)) {             // Check, if 4th array value (code) is in array
      $ns = $ns + $info[5];                   // plus to $ns, if yes
    } else {
      $s = $s + $info[5];                     // plus to $s, if no
    }
    unset($info);                             // clear array for next usage
  }
}

但是好像没有把线切割成数组。它只是向我显示线条,而不是划分为数组。我正在使用 Summernote 文本编辑器,它以行的形式发送数据。

因为您使用的是 $info[] = ...,所以您得到的是 2 层深度数组,而不是您的代码所期望的 1 层。 $info[] = ... 基本上意味着“将右侧添加到 $info 作为 one 元素”。所以如果右边是一个字符串并且 $info 在你得到 [0 => "my string"] 之前是空的。如果右边是一个数组,你会得到 [0 => [0 => "my", 1 => "array"]].

你明白我的意思了吗?您的代码正在向 $info 添加 one 元素,仅此而已。所以要访问 $info 中的任何内容,第一部分需要是 $info[0]。但是代码会查找第 4 个和第 5 个元素,但它们永远不会存在。另一方面,如果您要在第一个元素 中寻找第 4 个元素 。也就是说,第一个元素 $info[0] ,然后是其中的第 4 个元素: $info[0][4],那么你就会得到你想要的。

if(!empty($_POST['indata'])){
  $in_data = $_POST['indata'];                // Get POST data
  $fa = array("OCS", "CSE");                  // Make array
  $ns = 0;                                    // Init ns value
  $s = 0;                                  // Init ss value
  foreach(explode("\n",$in_data) as $line){   // Divide text to lines
    $info[] = explode("    ", $line);         // Divide line to values and put them to array 
    if(in_array($info[0][4], $fa)) {             // Check, if 4th array value (code) is in array
      $ns = $ns + (int) $info[0][5];                   // plus to $ns, if yes
    } else {
      $s = $s + (int) $info[0][5];                     // plus to $s, if no
    }

    unset($info);
  }
}

var_dump($ns, $s); // int(29) int(18)

版本 2. 如前所述,取消 $info 中的一级:

foreach(explode("\n",$in_data) as $line){
  $info = explode("    ", $line);
  if(in_array($info[4], $fa)) {
    $ns = $ns + (int) $info[5];
  } else {
    $s = $s + (int) $info[5];
  }
}

替代版本,正则表达式:

foreach(explode("\n",$in_data) as $line){
  $info = preg_split('/\s{4,}/', $line); // Split when 4 or more spaces
  if(in_array($info[3], $fa)) {
      $ns = $ns + (int) $info[4];
  } else {
      $s = $s + (int) $info[4];
  }
}

这样你就不会得到任何“垃圾专栏”:)。

编辑:我认为是 PHP 7.1 在添加不同类型的值(即字符串 + 数字)方面引入了更多“严格”。发出通知,“遇到格式不正确的数值”。但是,如果字符串是 cast/converted 作为数字,则在求和之前 PHP 将接受它。可以通过在字符串值前面添加 (int) 来完成转换。 (当然前提是它包含一个整数值,否则需要进行不同的转换)