Commit fce40a5
committed
[ext/standard] Specialize array_sum()/array_product() for packed long arrays
The per-element cost of array_sum()/array_product() is dominated by
the add_function/mul_function dispatch. The HashTable iteration itself
is already well-tuned via ZEND_HASH_FOREACH_VAL's branchless size
computation.
Split php_array_binop() into packed and hash paths, and within the
packed path add a specialized IS_LONG fast path that uses inlined
overflow-aware arithmetic (fast_long_add_function and
ZEND_SIGNED_MULTIPLY_LONG). Falls through to the generic helper on
overflow, non-LONG types, objects, resources, or strings, so the
PHP 8.3 warning behavior, operator overloading and BC casts for
resources/strings are preserved.
This follows the pattern in the recent array function optimizations
(PR #18158 array_map, PR #18157 array_find, PR #18180 array_reduce),
and was suggested in TimWolla's review of PR #18180.
Benchmarks (packed IS_LONG, -O2, median of 7 runs, Apple M1):
array_sum(range(1, N)) ~3.2x (N >= 1000)
array_product(small values) ~7.5x
array_product(range(1, N)) ~1.4x (N=100), neutral otherwise
packed_float / hash / mixed neutral (within noise)
Tests cover the overflow transition from fast path to generic, and
the integration with array_column() together with the PHP 8.3
nested-array warning behavior.1 parent 1195f27 commit fce40a5
File tree
5 files changed
+156
-35
lines changed- ext/standard
- tests/array
5 files changed
+156
-35
lines changed| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
292 | 292 | | |
293 | 293 | | |
294 | 294 | | |
| 295 | + | |
| 296 | + | |
295 | 297 | | |
296 | 298 | | |
297 | 299 | | |
| |||
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
6314 | 6314 | | |
6315 | 6315 | | |
6316 | 6316 | | |
| 6317 | + | |
| 6318 | + | |
| 6319 | + | |
| 6320 | + | |
| 6321 | + | |
| 6322 | + | |
| 6323 | + | |
| 6324 | + | |
| 6325 | + | |
| 6326 | + | |
| 6327 | + | |
| 6328 | + | |
| 6329 | + | |
| 6330 | + | |
| 6331 | + | |
| 6332 | + | |
| 6333 | + | |
| 6334 | + | |
| 6335 | + | |
| 6336 | + | |
| 6337 | + | |
| 6338 | + | |
| 6339 | + | |
| 6340 | + | |
| 6341 | + | |
| 6342 | + | |
| 6343 | + | |
| 6344 | + | |
| 6345 | + | |
| 6346 | + | |
| 6347 | + | |
| 6348 | + | |
| 6349 | + | |
| 6350 | + | |
| 6351 | + | |
| 6352 | + | |
| 6353 | + | |
| 6354 | + | |
| 6355 | + | |
| 6356 | + | |
6317 | 6357 | | |
6318 | 6358 | | |
6319 | 6359 | | |
6320 | 6360 | | |
6321 | | - | |
6322 | 6361 | | |
6323 | 6362 | | |
6324 | 6363 | | |
| |||
6329 | 6368 | | |
6330 | 6369 | | |
6331 | 6370 | | |
6332 | | - | |
6333 | | - | |
6334 | | - | |
6335 | | - | |
6336 | | - | |
6337 | | - | |
6338 | | - | |
6339 | | - | |
6340 | | - | |
6341 | | - | |
6342 | | - | |
6343 | | - | |
6344 | | - | |
6345 | | - | |
6346 | | - | |
6347 | 6371 | | |
6348 | | - | |
6349 | | - | |
6350 | | - | |
6351 | | - | |
6352 | | - | |
6353 | | - | |
6354 | | - | |
6355 | | - | |
6356 | | - | |
6357 | | - | |
6358 | | - | |
6359 | | - | |
6360 | | - | |
6361 | | - | |
6362 | | - | |
6363 | | - | |
6364 | | - | |
6365 | | - | |
| 6372 | + | |
| 6373 | + | |
| 6374 | + | |
| 6375 | + | |
| 6376 | + | |
| 6377 | + | |
| 6378 | + | |
| 6379 | + | |
| 6380 | + | |
| 6381 | + | |
| 6382 | + | |
| 6383 | + | |
| 6384 | + | |
| 6385 | + | |
| 6386 | + | |
| 6387 | + | |
| 6388 | + | |
| 6389 | + | |
| 6390 | + | |
| 6391 | + | |
| 6392 | + | |
| 6393 | + | |
| 6394 | + | |
| 6395 | + | |
| 6396 | + | |
| 6397 | + | |
| 6398 | + | |
| 6399 | + | |
| 6400 | + | |
| 6401 | + | |
| 6402 | + | |
6366 | 6403 | | |
6367 | | - | |
| 6404 | + | |
| 6405 | + | |
| 6406 | + | |
| 6407 | + | |
| 6408 | + | |
| 6409 | + | |
| 6410 | + | |
6368 | 6411 | | |
6369 | 6412 | | |
6370 | 6413 | | |
| |||
Lines changed: 22 additions & 0 deletions
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
| 1 | + | |
| 2 | + | |
| 3 | + | |
| 4 | + | |
| 5 | + | |
| 6 | + | |
| 7 | + | |
| 8 | + | |
| 9 | + | |
| 10 | + | |
| 11 | + | |
| 12 | + | |
| 13 | + | |
| 14 | + | |
| 15 | + | |
| 16 | + | |
| 17 | + | |
| 18 | + | |
| 19 | + | |
| 20 | + | |
| 21 | + | |
| 22 | + | |
Lines changed: 22 additions & 0 deletions
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
| 1 | + | |
| 2 | + | |
| 3 | + | |
| 4 | + | |
| 5 | + | |
| 6 | + | |
| 7 | + | |
| 8 | + | |
| 9 | + | |
| 10 | + | |
| 11 | + | |
| 12 | + | |
| 13 | + | |
| 14 | + | |
| 15 | + | |
| 16 | + | |
| 17 | + | |
| 18 | + | |
| 19 | + | |
| 20 | + | |
| 21 | + | |
| 22 | + | |
Lines changed: 32 additions & 0 deletions
| Original file line number | Diff line number | Diff line change | |
|---|---|---|---|
| |||
| 1 | + | |
| 2 | + | |
| 3 | + | |
| 4 | + | |
| 5 | + | |
| 6 | + | |
| 7 | + | |
| 8 | + | |
| 9 | + | |
| 10 | + | |
| 11 | + | |
| 12 | + | |
| 13 | + | |
| 14 | + | |
| 15 | + | |
| 16 | + | |
| 17 | + | |
| 18 | + | |
| 19 | + | |
| 20 | + | |
| 21 | + | |
| 22 | + | |
| 23 | + | |
| 24 | + | |
| 25 | + | |
| 26 | + | |
| 27 | + | |
| 28 | + | |
| 29 | + | |
| 30 | + | |
| 31 | + | |
| 32 | + | |
0 commit comments