2016-06-16 15 views
5

Tôi muốn hợp nhất nhiều mảng với nhau trong khi sử dụng các giá trị từ mảng đầu tiên và chỉ có các giá trị duy nhất. Có cách nào nhanh hơn sử dụng array_merge(), array_unique() và nhà điều hành + không?PHP array_merge() với tùy chọn chỉ có giá trị mảng và giá trị duy nhất đầu tiên?

function foo(...$params) { 
    $a = [ 
     'col1', 
     'col2_alias' => 'col2', 
     'col3' 
    ]; 
    $merged = array_merge($a, ...$params); 
    $unique = array_unique($merged); 
    print_r($merged); 
    print_r($unique); 
    print_r($a + $unique); 
} 

foo(
    ['col4', 'col5_alias' => 'col5', 'col6'], 
    ['col7', 'col1', 'col5_alias' => 'col5', 'col2_alias' => 'col10']); 

Chỉ cần sáp nhập các mảng mang lại cho tôi nhân đôi giá trị, và ghi đè giá trị trong mảng đầu tiên:

Array 
(
    [0] => col1 // duplicate 
    [col2_alias] => col10 // overwritten 
    [1] => col3 
    [2] => col4 
    [col5_alias] => col5 
    [3] => col6 
    [4] => col7 
    [5] => col1 // duplicate 
) 

Sử dụng array_unique() rõ ràng là ấn định giá trị nhân bản, nhưng không phải là giá trị ghi đè:

Array 
(
    [0] => col1 
    [col2_alias] => col10 
    [1] => col3 
    [2] => col4 
    [col5_alias] => col5 
    [3] => col6 
    [4] => col7 
) 

Sau khi sử dụng toán tử +, mảng là cách tôi muốn.

Array 
(
    [0] => col1 
    [col2_alias] => col2 
    [1] => col3 
    [2] => col4 
    [col5_alias] => col5 
    [3] => col6 
    [4] => col7 
) 
+0

Bạn sẽ cân nhắc sử dụng một thư viện bộ sưu tập? –

+1

Điều gì là xấu trong nhà điều hành + nếu nó hoạt động tốt? Nó có chậm không? – instead

+0

@ ÁlvaroGuimarães Thật không may, nó nằm trong mã cũ và việc thêm thư viện bộ sưu tập sẽ là một rắc rối. – GreeKatrina

Trả lời

0

Bạn có quyền giả định rằng sử dụng các chức năng array_merge, array_unique và nhà điều hành + sẽ chậm. Và tôi đã viết một chút mã để chuẩn tốc độ của từng kết hợp ...

Đây là mã mà ...

<?php 

class ArraySpeeds 
{ 
    public $la = ['col1', 'col2_alias' => 'col2', 'col3']; 
    public $a = ['col4', 'col5_alias' => 'col5', 'col6']; 
    public $b = ['col7', 'col1', 'col5_alias' => 'col5', 'col2_alias' => 'col10']; 
    public $c = []; 

    public function executionTime ($callback) 
    { 
     $start = microtime (true); 

     for ($i = 0; $i < 1000000; $i++) { 
      $callback(); 
     } 

     return round ((microtime (true) - $start) * 1000) . '/ms' . PHP_EOL; 
    } 

    public function getTimes() 
    { 
     $array_merge_time = $this->executionTime (function() { 
      $this->c[0] = array_merge ($this->la, $this->a, $this->b); 
     }); 

     $array_unique_time = $this->executionTime (function() { 
      $merged = array_merge ($this->la, $this->a, $this->b); 
      $this->c[1] = array_unique ($merged); 
     }); 

     $addition_time = $this->executionTime (function() { 
      $merged = array_merge ($this->la, $this->a, $this->b); 
      $unique = array_unique ($merged); 
      $this->c[2] = $this->la + $unique; 
     }); 

     $array_diff_time = $this->executionTime (function() { 
      $merged = array_merge ($this->a, $this->b); 
      $diffed = array_diff ($merged, $this->la); 

      $this->c[3] = array_merge ($diffed, $this->la); 
     }); 

     echo print_r ($this->c[0], true), PHP_EOL; 
     echo print_r ($this->c[1], true), PHP_EOL; 
     echo print_r ($this->c[2], true), PHP_EOL; 

     natsort ($this->c[3]); 
     echo print_r ($this->c[3], true), PHP_EOL; 

     echo 'array_merge: ', $array_merge_time; 
     echo 'array_unique: ', $array_unique_time; 
     echo 'addition: ', $addition_time; 
     echo 'array_diff: ', $array_diff_time; 
    } 
} 

$arrayspeeds = new ArraySpeeds(); 
$arrayspeeds->getTimes(); 

Đây là sản phẩm ...

Array 
(
    [0] => col1 
    [col2_alias] => col10 
    [1] => col3 
    [2] => col4 
    [col5_alias] => col5 
    [3] => col6 
    [4] => col7 
    [5] => col1 
) 

Array 
(
    [0] => col1 
    [col2_alias] => col10 
    [1] => col3 
    [2] => col4 
    [col5_alias] => col5 
    [3] => col6 
    [4] => col7 
) 

Array 
(
    [0] => col1 
    [col2_alias] => col2 
    [1] => col3 
    [2] => col4 
    [col5_alias] => col5 
    [3] => col6 
    [4] => col7 
) 

Array 
(
    [3] => col1 
    [col2_alias] => col2 
    [4] => col3 
    [0] => col4 
    [col5_alias] => col5 
    [1] => col6 
    [2] => col7 
) 

array_merge: 403/ms 
array_unique: 1039/ms 
addition: 1267/ms 
array_diff: 993/ms 

Bạn có thể thấy thời gian thực hiện lâu hơn với mỗi cuộc gọi hàm được thêm vào, với các hàm array_merge, array_unique và toán tử + là chậm nhất, nhanh gấp hai lần.

Tuy nhiên, việc sử dụng array_diff sẽ giúp bạn có được hiệu suất tốt với đầu ra chính xác nhưng không có sắp xếp chính xác. Thêm một cuộc gọi hàm natsort vào mảng sẽ sửa lỗi đó.

Ví dụ ...

function foo (...$params) 
{ 
    $a = [ 
     'col1', 
     'col2_alias' => 'col2', 
     'col3' 
    ]; 

    $diff = array_diff (array_merge (...$params), $a); 
    $merged = array_merge ($diff, $a); 
    natsort ($merged); 
    print_r ($merged); 
} 
+0

Tôi không cần chúng được sắp xếp, vì vậy công trình này hoàn hảo, cảm ơn bạn! – GreeKatrina

+0

Tôi đã bỏ phiếu cho câu trả lời này, nhưng vì một lý do nào đó nó vẫn cho thấy không. Nếu bạn không nhận được điểm đại diện, hãy cho SO biết. – GreeKatrina

1

Thực ra tôi không thấy bất kỳ vấn đề lớn nào với tập lệnh của bạn và tôi không biết tại sao bạn muốn cải thiện nó. Nhưng tôi đã viết triển khai chức năng của bạn và có vẻ như nó hoạt động nhanh hơn một chút, có giao diện (tôi cũng đã thêm một vài thông số khác để kiểm tra kết quả hàm):

<?php 

function foo(...$params) { 
    $a = [ 
     'col1', 
     'col2_alias' => 'col2', 
     'col3' 
    ]; 
    $merged = array_merge($a, ...$params); 
    $unique = array_unique($merged); 

    return $a + $unique; 
} 

function foo2(...$params) { 
    $a = [ 
     'col1', 
     'col2_alias' => 'col2', 
     'col3' 
    ]; 
    $merged = array_merge(array_diff(array_merge(...$params), $a), $a); 

    return $merged; 
} 

$timeFoo = microtime(true); 
for($i = 0; $i < 1000000; $i++) { 
    foo(
    ['col13', 'col5_alias' => 'col3', 'col8'], 
    ['col21', 'col5_alias' => 'col1', 'col9'], 
    ['col4', 'col5_alias' => 'col5', 'col6'], 
    ['col7', 'col1', 'col5_alias' => 'col5', 'col2_alias' => 'col10']); 
} 
$timeFoo = microtime(true) - $timeFoo; 


$timeFoo2 = microtime(true); 
for($i = 0; $i < 1000000; $i++) { 
    foo2(
    ['col13', 'col5_alias' => 'col3', 'col8'], 
    ['col21', 'col5_alias' => 'col1', 'col9'], 
    ['col4', 'col5_alias' => 'col5', 'col6'], 
    ['col7', 'col1', 'col5_alias' => 'col5', 'col2_alias' => 'col10']); 
} 
$timeFoo2 = microtime(true) - $timeFoo2; 

echo "'foo' time: $timeFoo \n"; 
echo "'foo2' time: $timeFoo2 \n"; 

Kết quả khác với thời gian theo thời gian, nhưng không quá nhiều:

'foo' time: 3.4310319423676 
'foo2' time: 2.5314350128174 

Vì vậy, nó giúp chúng tôi tăng hiệu suất gần 30%.

Các vấn đề liên quan