array_udiff似乎不起作用

时间:2017-05-16 10:31:26

标签: php arrays array-difference

我正在尝试将两个数组与array_udiff进行比较,但它非常适合。似乎array_udiff没有得到正确的答案。这是live demo。结果应该是一个空数组,但保留一个未过滤的元素。

<?php

$string = '{
  "sakiniai": [

      {
        "Faktas": "A",
        "value": "true"
      },
      {
        "Faktas": "B",
        "value": "true"
      },
      {
        "Faktas": "A",
        "value": "false"
      }
  ]
}';

$sakiniais = json_decode($string, true)['sakiniai'];


$v = $sakiniais[0];
$arr[] = $v;
$v['value'] = $v['value'] == "true" ? "false" : "true";
$arr[] = $v;
var_dump($arr);
var_dump($sakiniais);


print_r(array_udiff($arr, $sakiniais, function($a, $b){
/*
var_dump($a);
var_dump($b);
var_dump($a == $b);
echo "\n\n\n";
*/
return $a == $b ? 0 : -1;}
));

输出

    array(2) {
  [0]=>
  array(2) {
    ["Faktas"]=>
    string(1) "A"
    ["value"]=>
    string(4) "true"
  }
  [1]=>
  array(2) {
    ["Faktas"]=>
    string(1) "A"
    ["value"]=>
    string(5) "false"
  }
}
array(3) {
  [0]=>
  array(2) {
    ["Faktas"]=>
    string(1) "A"
    ["value"]=>
    string(4) "true"
  }
  [1]=>
  array(2) {
    ["Faktas"]=>
    string(1) "B"
    ["value"]=>
    string(4) "true"
  }
  [2]=>
  array(2) {
    ["Faktas"]=>
    string(1) "A"
    ["value"]=>
    string(5) "false"
  }
}
Array
(
    [1] => Array
        (
            [Faktas] => A
            [value] => false
        )

)

2 个答案:

答案 0 :(得分:2)

问题是array_udiff没有执行所有值之间的比较,这似乎是由比较函数引起的。

array_udiff()期望可调用函数是一个真正的比较函数,但是你总是返回0和-1,但从不返回1.

在完成工作之前,array_udiff()尝试对这两个数组进行排序并删除重复数据。如果它不依赖于您的比较功能,它就无法执行所有必需的比较,并且某些值会跳过&#34;跳过&#34;。

查看the documentation中的所有评论,特别是napcoder comment

  

请注意,比较功能也在内部使用,以便订购   数组并选择在下一轮比较哪个元素。

     

如果你的比较函数没有真正比较(即。如果,则返回0)   元素是等于,否则1,你会收到一个意外的   结果

通过查看数组来演示

$ ARR

array(2) {
  [0]=>
  array(2) {
    ["Faktas"]=>
    string(1) "A"
    ["value"]=>
    string(4) "true"
  }
  [1]=>
  array(2) {
    ["Faktas"]=>
    string(1) "A"
    ["value"]=>
    string(5) "false"
  }
}

和$ sakiniais

array(3) {
  [0]=>
  array(2) {
    ["Faktas"]=>
    string(1) "A"
    ["value"]=>
    string(4) "true"
  }
  [1]=>
  array(2) {
    ["Faktas"]=>
    string(1) "B"
    ["value"]=>
    string(4) "true"
  }
  [2]=>
  array(2) {
    ["Faktas"]=>
    string(1) "A"
    ["value"]=>
    string(5) "false"
  }
}

您应该期望测试两个阵列之间的所有组合,但测试的组合(下面)不包括A-False与A-False

array(2) {
    ["Faktas"]=>
    string(1) "A"
    ["value"]=>
    string(4) "true"
}
array(2) {
    ["Faktas"]=>
    string(1) "A"
    ["value"]=>
    string(5) "false"
}
bool(false)



array(2) {
    ["Faktas"]=>
    string(1) "A"
    ["value"]=>
    string(4) "true"
}
array(2) {
    ["Faktas"]=>
    string(1) "B"
    ["value"]=>
    string(4) "true"
}
bool(false)



array(2) {
    ["Faktas"]=>
    string(1) "B"
    ["value"]=>
    string(4) "true"
}
array(2) {
    ["Faktas"]=>
    string(1) "A"
    ["value"]=>
    string(5) "false"
}
bool(false)



array(2) {
    ["Faktas"]=>
    string(1) "A"
    ["value"]=>
    string(4) "true"
}
array(2) {
    ["Faktas"]=>
    string(1) "A"
    ["value"]=>
    string(4) "true"
}
bool(true)



array(2) {
    ["Faktas"]=>
    string(1) "A"
    ["value"]=>
    string(4) "true"
}
array(2) {
    ["Faktas"]=>
    string(1) "A"
    ["value"]=>
    string(5) "false"
}
bool(false)



array(2) {
    ["Faktas"]=>
    string(1) "A"
    ["value"]=>
    string(5) "false"
}
array(2) {
    ["Faktas"]=>
    string(1) "B"
    ["value"]=>
    string(4) "true"
}
bool(false)

this post的正确答案中,对于array_udiff的工作方式还有一些其他有用的见解

您可以像这样更改退货声明

if ($a < $b) {
    return -1;
} elseif ($a > $b) {
    return 1;
} else {
    return 0;
}

(如果您想知道如何以更小/更大的比较比较两个数组,请查看this link,在&#34;与各种类型的比较&#34;以及&#34;示例中#2标准数组比较的转录&#34;例子)

答案 1 :(得分:0)

没什么奇怪的,一切都按预期工作。看看数组比较:

$arraysAreEqual = ($a == $b); // TRUE if $a and $b have the same key/value pairs.
$arraysAreEqual = ($a === $b); // TRUE if $a and $b have the same key/value pairs in the same order and of the same types.

所以,$ arr [0] == $ sakiniai [0]为真,但$ arr [1] == $ sakiniai [2]为假,输出为$ arr [1]

$ ARR

array(2) {
  [0]=>
  array(2) {
    ["Faktas"]=>
    string(1) "A"
    ["value"]=>
    string(4) "true"
  }
  [1]=>
  array(2) {
    ["Faktas"]=>
    string(1) "A"
    ["value"]=>
    string(5) "false"
  }
}

$ sakiniai

array(3) {
  [0]=>
  array(2) {
    ["Faktas"]=>
    string(1) "A"
    ["value"]=>
    string(4) "true"
  }
  [1]=>
  array(2) {
    ["Faktas"]=>
    string(1) "B"
    ["value"]=>
    string(4) "true"
  }
  [2]=>
  array(2) {
    ["Faktas"]=>
    string(1) "A"
    ["value"]=>
    string(5) "false"
  }
}

结果

Array
(
    [1] => Array
        (
            [Faktas] => A
            [value] => false
        )

)