Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

array_filter: Remove unnecessary refcounting #17538

Merged
merged 1 commit into from
Jan 21, 2025

Conversation

TimWolla
Copy link
Member

This syncs the implementation with the updated implementation of array_find() in #17536. For the following test script:

<?php

$array = range(1, 8000);

$result = 0;
for ($i = 0; $i < 4000; $i++) {
	$result += count(array_filter($array, static function ($item) {
		return $item <= 4000;
	}));
}
var_dump($result);

This change results in:

Benchmark 1: /tmp/before array_filter.php
  Time (mean ± σ):     696.9 ms ±  16.3 ms    [User: 692.9 ms, System: 3.5 ms]
  Range (min … max):   681.6 ms … 731.5 ms    10 runs

Benchmark 2: /tmp/after array_filter.php
  Time (mean ± σ):     637.5 ms ±   5.6 ms    [User: 633.6 ms, System: 3.8 ms]
  Range (min … max):   630.2 ms … 648.6 ms    10 runs

Summary
  /tmp/after array_filter.php ran
    1.09 ± 0.03 times faster than /tmp/before array_filter.php

Or as reported by perf:

# Samples: 2K of event 'cpu_core/cycles/'
# Event count (approx.): 2567197440
#
# Overhead  Command  Shared Object         Symbol
# ........  .......  ....................  ........................................................
#
    37.02%  before   before                [.] zend_call_function
    15.50%  before   before                [.] execute_ex
    10.60%  before   before                [.] zif_array_filter
     9.43%  before   before                [.] zend_hash_index_add_new
     9.13%  before   before                [.] ZEND_IS_SMALLER_OR_EQUAL_SPEC_TMPVARCV_CONST_HANDLER
     8.46%  before   before                [.] zend_init_func_execute_data
     3.78%  before   before                [.] zval_add_ref
     3.47%  before   before                [.] zval_ptr_dtor
     1.17%  before   before                [.] zend_is_true

vs

# Samples: 2K of event 'cpu_core/cycles/'
# Event count (approx.): 2390202140
#
# Overhead  Command  Shared Object         Symbol
# ........  .......  ....................  ........................................................
#
    36.87%  after    after                 [.] zend_call_function
    20.46%  after    after                 [.] execute_ex
     8.22%  after    after                 [.] zend_init_func_execute_data
     7.94%  after    after                 [.] zend_hash_index_add_new
     7.89%  after    after                 [.] zif_array_filter
     6.28%  after    after                 [.] ZEND_IS_SMALLER_OR_EQUAL_SPEC_TMPVARCV_CONST_HANDLER
     3.95%  after    after                 [.] zval_add_ref
     2.23%  after    after                 [.] zend_is_true

This syncs the implementation with the updated implementation of `array_find()`
in php#17536. For the following test script:

    <?php

    $array = range(1, 8000);

    $result = 0;
    for ($i = 0; $i < 4000; $i++) {
    	$result += count(array_filter($array, static function ($item) {
    		return $item <= 4000;
    	}));
    }
    var_dump($result);

This change results in:

    Benchmark 1: /tmp/before array_filter.php
      Time (mean ± σ):     696.9 ms ±  16.3 ms    [User: 692.9 ms, System: 3.5 ms]
      Range (min … max):   681.6 ms … 731.5 ms    10 runs

    Benchmark 2: /tmp/after array_filter.php
      Time (mean ± σ):     637.5 ms ±   5.6 ms    [User: 633.6 ms, System: 3.8 ms]
      Range (min … max):   630.2 ms … 648.6 ms    10 runs

    Summary
      /tmp/after array_filter.php ran
        1.09 ± 0.03 times faster than /tmp/before array_filter.php

Or as reported by perf:

    # Samples: 2K of event 'cpu_core/cycles/'
    # Event count (approx.): 2567197440
    #
    # Overhead  Command  Shared Object         Symbol
    # ........  .......  ....................  ........................................................
    #
        37.02%  before   before                [.] zend_call_function
        15.50%  before   before                [.] execute_ex
        10.60%  before   before                [.] zif_array_filter
         9.43%  before   before                [.] zend_hash_index_add_new
         9.13%  before   before                [.] ZEND_IS_SMALLER_OR_EQUAL_SPEC_TMPVARCV_CONST_HANDLER
         8.46%  before   before                [.] zend_init_func_execute_data
         3.78%  before   before                [.] zval_add_ref
         3.47%  before   before                [.] zval_ptr_dtor
         1.17%  before   before                [.] zend_is_true

vs

    # Samples: 2K of event 'cpu_core/cycles/'
    # Event count (approx.): 2390202140
    #
    # Overhead  Command  Shared Object         Symbol
    # ........  .......  ....................  ........................................................
    #
        36.87%  after    after                 [.] zend_call_function
        20.46%  after    after                 [.] execute_ex
         8.22%  after    after                 [.] zend_init_func_execute_data
         7.94%  after    after                 [.] zend_hash_index_add_new
         7.89%  after    after                 [.] zif_array_filter
         6.28%  after    after                 [.] ZEND_IS_SMALLER_OR_EQUAL_SPEC_TMPVARCV_CONST_HANDLER
         3.95%  after    after                 [.] zval_add_ref
         2.23%  after    after                 [.] zend_is_true
}
}
if (use_type != ARRAY_FILTER_USE_KEY) {
ZVAL_COPY(&args[0], operand);
ZVAL_COPY_VALUE(&args[0], operand);
}
fci.params = args;
Copy link
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Somewhat surprisingly, moving this line out of the loop into the ZEND_FCI_INITIALIZED(fci) decreases performance. I don't have an explanation for that.

Copy link
Member

@Girgias Girgias left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

MSTM

@TimWolla TimWolla merged commit 1aaf2b1 into php:master Jan 21, 2025
10 checks passed
@TimWolla TimWolla deleted the array-filter-optimization branch January 21, 2025 14:43
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants