Skip to content

Change datastructure in Components #19043

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

Open
wants to merge 2 commits into
base: main
Choose a base branch
from

Conversation

Trashtalk217
Copy link
Contributor

@Trashtalk217 Trashtalk217 commented May 3, 2025

Objective

We've been looking at moving to sparse ComponentIds for a while now, partly in preparation for components as entities.

Solution

As such, I'm changing the Vec<Option<ComponentInfo>> into a new HybridMap, which combines the Vec storage with a HashMap for component indices below a certain threshold.

Performance

Running the ECS performance tests, I got the following result. These are sorted from best to worst, with a negative percentage meaning a reduction in time. Of all the tests, 255 improved, and 139 regressed, although most stayed roughly equal.

I've tested with two thresholds: 128 and 256, and 128 was better. Although I will admit that my laptop is trying its heart out and I'm somewhat doubtful it can produce reliable results. The 128 to 256 jump shouldn't have made the difference it did.

Benchmark results
Name Change Uncertainty
none_changed_detection/5000_entities_ecs__change_detection__Sparse -91.69 0.0
empty_archetypes/par_for_each/10000 -90.54 0.0
none_changed_detection/50000_entities_ecs__change_detection__Sparse -90.26 0.0
few_changed_detection/5000_entities_ecs__change_detection__Sparse -90.06 0.0
empty_archetypes/par_for_each/2000 -88.3 0.01
no_archetypes/system_count/100 -87.04 0.0
empty_archetypes/par_for_each/500 -86.81 0.01
multiple_archetypes_none_changed_detection/5_archetypes_10_entities_ecs__change_detection__Sparse -86.73 0.0
empty_archetypes/for_each/5000 -86.21 0.01
empty_archetypes/iter/10000 -86.16 0.01
multiple_archetypes_none_changed_detection/5_archetypes_100_entities_ecs__change_detection__Sparse -85.96 0.0
empty_archetypes/iter/500 -85.78 0.01
empty_archetypes/for_each/100 -85.4 0.01
all_changed_detection/50000_entities_ecs__change_detection__Sparse -85.3 0.0
ecs__entity_cloning__single/reflect -84.6 0.01
empty_archetypes/for_each/1000 -84.01 0.01
multiple_archetypes_none_changed_detection/20_archetypes_10_entities_ecs__change_detection__Sparse -83.46 0.01
empty_archetypes/par_for_each/10 -80.82 0.02
multiple_archetypes_none_changed_detection/20_archetypes_100_entities_ecs__change_detection__Sparse -80.8 0.01
no_archetypes/system_count/60 -75.44 0.02
multiple_archetypes_none_changed_detection/5_archetypes_1000_entities_ecs__change_detection__Sparse -74.61 0.02
insert_simple/unbatched -73.77 0.03
all_added_detection/5000_entities_ecs__change_detection__Sparse -70.64 0.03
all_added_detection/50000_entities_ecs__change_detection__Sparse -68.74 0.03
all_changed_detection/5000_entities_ecs__change_detection__Sparse -68.06 0.03
query_get/50000_entities_table -66.26 0.01
multiple_archetypes_none_changed_detection/20_archetypes_1000_entities_ecs__change_detection__Sparse -66.15 0.04
few_changed_detection/50000_entities_ecs__change_detection__Sparse -65.14 0.04
multiple_archetypes_none_changed_detection/100_archetypes_10_entities_ecs__change_detection__Sparse -64.02 0.05
multiple_archetypes_none_changed_detection/5_archetypes_10000_entities_ecs__change_detection__Sparse -63.9 0.04
entity_hash/entity_set_lookup_miss_gen/3162 -59.33 0.0
world_query_iter/50000_entities_sparse -58.03 0.01
query_get/50000_entities_sparse -56.67 0.01
world_get/50000_entities_table -55.75 0.01
fake_commands/8000_commands -55.73 0.01
fake_commands/6000_commands -55.1 0.01
entity_hash/entity_set_lookup_hit/10000 -54.83 0.0
empty_commands/0_entities -54.39 0.01
sized_commands_512_bytes/2000_commands -54.37 0.01
entity_hash/entity_set_lookup_miss_gen/316 -53.89 0.0
fake_commands/4000_commands -53.88 0.0
world_get/50000_entities_sparse -53.64 0.0
entity_hash/entity_set_lookup_hit/100 -53.51 0.0
run_empty_schedule/Simple -53.4 0.0
world_query_iter/50000_entities_table -53.38 0.0
entity_hash/entity_set_lookup_hit/1000 -53.37 0.0
entity_hash/entity_set_lookup_miss_gen/10000 -53.33 0.0
entity_hash/entity_set_lookup_hit/316 -53.3 0.0
fake_commands/2000_commands -53.3 0.01
sized_commands_512_bytes/4000_commands -53.21 0.01
world_entity/50000_entities -53.1 0.0
world_query_get/50000_entities_table -53.09 0.01
entity_hash/entity_set_build/10000 -53.03 0.0
spawn_commands/8000_entities -52.91 0.0
world_query_for_each/50000_entities_table -52.87 0.0
entity_hash/entity_set_build/3162 -52.81 0.0
sized_commands_0_bytes/8000_commands -52.81 0.0
entity_hash/entity_set_build/1000 -52.75 0.0
sized_commands_0_bytes/6000_commands -52.63 0.0
spawn_commands/2000_entities -52.56 0.0
sized_commands_0_bytes/4000_commands -52.55 0.0
entity_hash/entity_set_lookup_hit/3162 -52.47 0.0
run_empty_schedule/MultiThreaded -52.46 0.0
entity_hash/entity_set_lookup_miss_gen/100 -52.43 0.0
insert_commands/insert_batch -52.28 0.01
param_combinator_system/8_piped_systems -52.19 0.01
world_query_get/50000_entities_sparse_wide -52.13 0.0
spawn_commands/4000_entities -52.07 0.0
despawn_world/1000_entities -51.98 0.0
despawn_world_recursive/10000_entities -51.97 0.0
entity_hash/entity_set_build/100 -51.95 0.0
sized_commands_12_bytes/4000_commands -51.82 0.0
sized_commands_12_bytes/2000_commands -51.72 0.0
sized_commands_0_bytes/2000_commands -51.68 0.01
build_schedule/1000_schedule -51.65 0.0
sized_commands_512_bytes/6000_commands -51.53 0.02
build_schedule/500_schedule -51.5 0.0
despawn_world_recursive/1000_entities -51.47 0.0
world_query_get/50000_entities_sparse -51.47 0.01
spawn_commands/6000_entities -51.43 0.0
despawn_world_recursive/10_entities -51.39 0.01
entity_hash/entity_set_build/316 -51.31 0.0
param_combinator_system/8_dyn_params_system -51.1 0.02
despawn_world/10000_entities -51.06 0.01
insert_commands/insert -50.99 0.01
despawn_world_recursive/100_entities -50.98 0.01
world_query_for_each/50000_entities_sparse -50.96 0.01
entity_hash/entity_set_lookup_miss_id/316 -50.76 0.0
despawn_world/100_entities -50.69 0.01
despawn_world/10_entities -50.64 0.01
entity_hash/entity_set_lookup_miss_id/1000 -50.45 0.0
sized_commands_512_bytes/8000_commands -50.38 0.02
sized_commands_12_bytes/6000_commands -50.07 0.01
world_query_get/50000_entities_table_wide -49.71 0.01
entity_hash/entity_set_lookup_miss_id/3162 -49.68 0.0
entity_hash/entity_set_lookup_miss_id/100 -49.62 0.0
entity_hash/entity_set_lookup_miss_id/10000 -49.57 0.0
run_empty_schedule/SingleThreaded -48.26 0.0
insert_commands/insert_or_spawn_batch -48.11 0.01
param_combinator_system/8_variant_param_set_system -47.56 0.01
sized_commands_12_bytes/8000_commands -47.43 0.01
spawn_world/10_entities -46.79 0.01
despawn_world/1_entities -46.55 0.01
spawn_world/1000_entities -45.44 0.01
despawn_world_recursive/1_entities -45.39 0.01
query_get_many_2/50000_calls_table -45.1 0.0
spawn_world/1_entities -44.8 0.01
spawn_world/100_entities -44.64 0.01
build_schedule/1000_schedule_no_constraints -44.41 0.0
query_get_many_5/50000_calls_sparse -43.33 0.0
spawn_world/10000_entities -42.33 0.01
query_get_many_5/50000_calls_table -41.53 0.01
query_get_many_2/50000_calls_sparse -40.5 0.01
entity_hash/entity_set_lookup_miss_gen/1000 -40.14 0.0
build_schedule/500_schedule_no_constraints -38.96 0.01
events_send/size_4_events_1000 -38.95 0.0
query_get_many_10/50000_calls_sparse -36.18 0.0
query_get_many_10/50000_calls_table -35.01 0.0
events_send/size_4_events_100 -34.93 0.0
added_archetypes/archetype_count/200 -29.26 0.08
events_send/size_16_events_100 -23.47 0.0
observe/trigger_targets_simple_10000_entity -19.03 0.01
busy_systems/04x_entities_12_systems -10.77 0.01
busy_systems/03x_entities_03_systems -10.01 0.02
run_condition_no/036_systems -10.0 0.02
contrived/02x_entities_09_systems -9.58 0.01
run_condition_no/066_systems -9.46 0.03
contrived/03x_entities_15_systems -9.21 0.01
contrived/04x_entities_09_systems -9.07 0.01
run_condition_no/091_systems -8.94 0.01
contrived/02x_entities_06_systems -8.93 0.01
contrived/04x_entities_06_systems -8.62 0.02
contrived/04x_entities_03_systems -8.44 0.01
contrived/03x_entities_06_systems -7.82 0.01
contrived/02x_entities_12_systems -7.45 0.01
iter_simple/foreach_wide -7.45 0.01
run_condition_no/001_systems -7.26 0.02
contrived/01x_entities_06_systems -7.25 0.02
busy_systems/05x_entities_06_systems -7.23 0.02
contrived/04x_entities_12_systems -7.13 0.01
run_condition_no/071_systems -6.93 0.03
contrived/04x_entities_15_systems -6.79 0.01
contrived/03x_entities_12_systems -6.77 0.01
events_send/size_16_events_50000 -6.76 0.01
events_send/size_4_events_50000 -6.52 0.01
contrived/01x_entities_15_systems -6.48 0.02
busy_systems/04x_entities_15_systems -6.3 0.02
contrived/01x_entities_12_systems -6.1 0.02
contrived/03x_entities_09_systems -6.04 0.01
busy_systems/05x_entities_09_systems -5.66 0.02
busy_systems/03x_entities_06_systems -5.55 0.02
contrived/03x_entities_03_systems -5.55 0.01
busy_systems/03x_entities_12_systems -5.49 0.01
events_send/size_4_events_10000 -5.11 0.01
empty_archetypes/iter/10 -5.02 0.03
heavy_compute/base -4.98 0.02
busy_systems/04x_entities_06_systems -4.63 0.02
busy_systems/01x_entities_15_systems -4.48 0.01
contrived/05x_entities_03_systems -4.46 0.02
insert_simple/base -4.46 0.01
iter_fragmented/foreach -4.25 0.02
events_send/size_16_events_1000 -4.18 0.0
busy_systems/04x_entities_09_systems -4.17 0.03
run_condition_no/061_systems -4.07 0.01
busy_systems/01x_entities_09_systems -3.99 0.01
busy_systems/01x_entities_06_systems -3.98 0.01
run_condition_no/046_systems -3.9 0.01
busy_systems/03x_entities_15_systems -3.76 0.02
run_condition_yes_using_query/001_systems -3.7 0.02
events_send/size_16_events_10000 -3.69 0.01
iter_simple/wide -3.64 0.01
run_condition_no/096_systems -3.48 0.02
busy_systems/03x_entities_09_systems -3.38 0.02
events_send/size_512_events_1000 -3.36 0.01
run_condition_no/081_systems -3.12 0.01
run_condition_no/051_systems -3.02 0.03
contrived/02x_entities_15_systems -2.95 0.01
busy_systems/01x_entities_03_systems -2.91 0.01
empty_archetypes/iter/2000 -2.7 0.03
build_schedule/100_schedule -2.69 0.0
run_condition_no/006_systems -2.58 0.0
few_changed_detection/5000_entities_ecs__change_detection__Table -2.57 0.01
run_condition_no/031_systems -2.53 0.02
added_archetypes/archetype_count/1000 -2.49 0.01
run_condition_no/086_systems -2.35 0.02
add_remove/table -2.33 0.0
add_remove_big/sparse_set -2.24 0.01
no_archetypes/system_count/20 -2.24 0.01
run_condition_no/016_systems -2.2 0.02
empty_systems/002_systems -2.16 0.01
run_condition_yes_using_query/011_systems -2.03 0.01
empty_systems/003_systems -1.92 0.02
empty_systems/090_systems -1.9 0.01
run_condition_no/056_systems -1.88 0.01
empty_systems/070_systems -1.86 0.01
no_archetypes/system_count/40 -1.86 0.01
empty_systems/080_systems -1.72 0.01
observe/trigger_simple -1.68 0.01
run_condition_yes_using_resource/096_systems -1.63 0.0
run_condition_yes_using_resource/036_systems -1.62 0.01
iter_fragmented_sparse/foreach -1.49 0.01
all_changed_detection/50000_entities_ecs__change_detection__Table -1.48 0.02
few_changed_detection/50000_entities_ecs__change_detection__Table -1.43 0.01
event_propagation/four_event_types -1.4 0.0
empty_systems/005_systems -1.39 0.01
all_changed_detection/5000_entities_ecs__change_detection__Table -1.38 0.01
empty_systems/085_systems -1.36 0.0
empty_systems/075_systems -1.28 0.0
run_condition_no/101_systems -1.27 0.01
empty_systems/055_systems -1.26 0.0
empty_systems/040_systems -1.23 0.01
run_condition_yes_using_resource/076_systems -1.21 0.01
iter_simple/sparse_set -1.14 0.01
events_send/size_512_events_100 -1.09 0.01
run_condition_yes_using_resource/051_systems -1.08 0.0
multiple_archetypes_none_changed_detection/100_archetypes_100_entities_ecs__change_detection__Sparse -1.06 0.02
empty_systems/004_systems -1.03 0.02
empty_systems/100_systems -1.01 0.0
run_condition_yes_using_query/066_systems -0.99 0.0
run_condition_yes_using_query/026_systems -0.97 0.01
contrived/05x_entities_09_systems -0.96 0.01
empty_systems/030_systems -0.95 0.01
busy_systems/04x_entities_03_systems -0.9 0.02
run_condition_no/076_systems -0.85 0.01
empty_systems/065_systems -0.81 0.01
iter_simple/base -0.75 0.01
event_propagation/single_event_type_no_listeners -0.68 0.01
empty_systems/095_systems -0.67 0.01
multiple_archetypes_none_changed_detection/100_archetypes_1000_entities_ecs__change_detection__Sparse -0.6 0.02
run_condition_yes/031_systems -0.54 0.01
iter_fragmented_sparse/wide -0.52 0.01
run_condition_yes_using_resource/031_systems -0.52 0.01
run_condition_yes_using_query/046_systems -0.51 0.0
run_condition_yes_using_resource/086_systems -0.5 0.0
run_condition_no/026_systems -0.45 0.01
run_condition_yes_using_query/031_systems -0.45 0.01
empty_systems/060_systems -0.42 0.0
iter_fragmented/base -0.41 0.01
run_condition_yes/091_systems -0.36 0.01
run_condition_yes/096_systems -0.34 0.01
iter_simple/foreach -0.33 0.01
busy_systems/05x_entities_15_systems -0.32 0.01
run_condition_yes_using_query/071_systems -0.28 0.0
added_archetypes/archetype_count/5000 -0.27 0.01
busy_systems/05x_entities_12_systems -0.26 0.01
empty_systems/045_systems -0.22 0.0
run_condition_yes_using_query/101_systems -0.18 0.0
run_condition_yes_using_resource/081_systems -0.17 0.0
run_condition_yes_using_resource/101_systems -0.15 0.0
run_condition_no/041_systems -0.14 0.01
iter_simple/system -0.08 0.01
run_condition_yes/061_systems -0.08 0.0
added_archetypes/archetype_count/10000 -0.07 0.01
multiple_archetypes_none_changed_detection/100_archetypes_10000_entities_ecs__change_detection__Sparse -0.03 0.01
run_condition_yes_using_query/096_systems -0.03 0.01
contrived/02x_entities_03_systems 0.01 0.01
run_condition_yes/101_systems 0.03 0.0
added_archetypes/archetype_count/500 0.04 0.01
run_condition_yes_using_resource/016_systems 0.05 0.01
run_condition_yes_using_resource/071_systems 0.07 0.0
added_archetypes/archetype_count/2000 0.09 0.01
busy_systems/05x_entities_03_systems 0.1 0.03
empty_systems/001_systems 0.1 0.01
empty_systems/020_systems 0.13 0.01
run_condition_yes/026_systems 0.13 0.01
run_condition_yes_using_resource/091_systems 0.15 0.0
run_condition_yes/081_systems 0.17 0.01
par_iter_simple/hybrid 0.18 0.01
empty_systems/025_systems 0.2 0.01
run_condition_yes_using_query/051_systems 0.2 0.0
empty_systems/035_systems 0.23 0.01
empty_systems/015_systems 0.24 0.01
empty_systems/050_systems 0.32 0.0
run_condition_yes_using_query/006_systems 0.37 0.01
contrived/05x_entities_12_systems 0.38 0.01
run_condition_yes/086_systems 0.4 0.01
add_remove_very_big/table 0.42 0.0
run_condition_yes_using_query/076_systems 0.42 0.0
run_condition_yes_using_query/056_systems 0.43 0.0
run_condition_yes_using_query/086_systems 0.48 0.0
iter_fragmented_sparse/base 0.5 0.0
run_condition_yes/066_systems 0.5 0.0
run_condition_yes/071_systems 0.5 0.0
run_condition_yes_using_query/081_systems 0.52 0.0
run_condition_yes/041_systems 0.54 0.01
run_condition_yes/046_systems 0.54 0.01
iter_simple/wide_sparse_set 0.61 0.01
multiple_archetypes_none_changed_detection/20_archetypes_10000_entities_ecs__change_detection__Sparse 0.63 0.01
run_condition_yes_using_resource/041_systems 0.63 0.01
run_condition_yes_using_query/061_systems 0.69 0.0
run_condition_yes_using_query/041_systems 0.7 0.01
run_condition_yes_using_resource/066_systems 0.7 0.01
run_condition_yes/006_systems 0.72 0.02
run_condition_yes_using_query/036_systems 0.72 0.01
run_condition_yes/056_systems 0.82 0.01
run_condition_yes_using_query/021_systems 0.87 0.01
add_remove/sparse_set 0.97 0.01
iter_simple/foreach_sparse_set 0.97 0.01
run_condition_no/021_systems 0.98 0.02
schedule/base 1.0 0.01
run_condition_yes/016_systems 1.08 0.01
run_condition_yes_using_resource/061_systems 1.13 0.0
contrived/05x_entities_06_systems 1.45 0.02
run_condition_yes_using_resource/026_systems 1.45 0.01
add_remove_big/table 1.47 0.01
busy_systems/02x_entities_06_systems 1.47 0.01
run_condition_yes_using_resource/001_systems 1.53 0.02
events_send/size_512_events_50000 1.55 0.0
run_condition_yes_using_query/091_systems 1.59 0.01
contrived/01x_entities_09_systems 1.7 0.02
iter_fragmented/wide 1.7 0.01
run_condition_yes/051_systems 1.7 0.0
run_condition_yes/036_systems 1.74 0.01
run_condition_yes_using_resource/046_systems 1.88 0.0
run_condition_yes_using_resource/006_systems 1.9 0.01
empty_systems/010_systems 1.93 0.01
run_condition_no/011_systems 2.15 0.03
run_condition_yes_using_resource/056_systems 2.26 0.0
contrived/01x_entities_03_systems 2.28 0.01
run_condition_yes_using_query/016_systems 2.32 0.01
run_condition_yes/076_systems 2.43 0.02
no_archetypes/system_count/80 2.48 0.01
run_condition_yes_using_resource/011_systems 2.56 0.01
ecs__entity_cloning__hierarchy_many/reflect 2.82 0.01
run_condition_yes_using_resource/021_systems 2.86 0.01
event_propagation/single_event_type 3.1 0.01
contrived/05x_entities_15_systems 3.67 0.01
run_condition_yes/021_systems 3.77 0.02
iter_simple/foreach_wide_sparse_set 4.07 0.01
events_send/size_512_events_10000 4.22 0.01
run_condition_yes/011_systems 4.54 0.01
multiple_archetypes_none_changed_detection/100_archetypes_10_entities_ecs__change_detection__Table 4.73 0.05
added_archetypes/archetype_count/100 4.75 0.02
run_condition_yes/001_systems 4.9 0.01
iter_fragmented_sparse/foreach_wide 4.91 0.01
busy_systems/02x_entities_15_systems 5.39 0.01
iter_fragmented/foreach_wide 5.97 0.01
busy_systems/02x_entities_09_systems 6.29 0.02
iter_simple/foreach_hybrid 6.38 0.01
build_schedule/100_schedule_no_constraints 6.39 0.01
busy_systems/02x_entities_12_systems 6.4 0.01
empty_systems/000_systems 6.77 0.03
busy_systems/02x_entities_03_systems 7.15 0.02
ecs__entity_cloning__hierarchy_tall/clone 7.4 0.1
ecs__entity_cloning__hierarchy_wide/clone 7.9 0.01
ecs__entity_cloning__hierarchy_tall/reflect 8.7 0.03
ecs__entity_cloning__hierarchy_wide/reflect 8.71 0.01
multiple_archetypes_none_changed_detection/5_archetypes_10_entities_ecs__change_detection__Table 9.22 0.01
busy_systems/01x_entities_12_systems 9.39 0.01
no_archetypes/system_count/0 9.97 0.01
empty_archetypes/for_each/10000 10.08 0.01
ecs__entity_cloning__hierarchy_many/clone 10.19 0.02
empty_archetypes/par_for_each/5000 10.61 0.01
empty_archetypes/for_each/500 10.64 0.02
empty_archetypes/iter/5000 12.11 0.02
empty_archetypes/par_for_each/1000 12.87 0.01
iter_fragmented(4096)_empty/foreach_table 12.93 0.01
empty_archetypes/iter/1000 13.12 0.01
empty_archetypes/for_each/10 13.65 0.01
empty_archetypes/par_for_each/100 14.19 0.02
empty_archetypes/iter/100 14.57 0.01
ecs__entity_cloning__single/clone 14.69 0.02
empty_archetypes/for_each/2000 15.53 0.02
par_iter_simple/with_1000_fragment 16.54 0.02
iter_fragmented(4096)_empty/foreach_sparse 17.68 0.01
events_iter/size_16_events_50000 18.23 0.03
events_iter/size_512_events_100 19.49 0.01
events_iter/size_512_events_1000 19.76 0.01
par_iter_simple/with_0_fragment 19.98 0.01
events_iter/size_512_events_50000 21.61 0.01
all_added_detection/5000_entities_ecs__change_detection__Table 22.12 0.01
events_iter/size_512_events_10000 22.15 0.0
events_iter/size_4_events_100 22.99 0.01
events_iter/size_16_events_1000 23.22 0.02
par_iter_simple/with_100_fragment 23.32 0.01
multiple_archetypes_none_changed_detection/20_archetypes_10_entities_ecs__change_detection__Table 23.6 0.02
all_added_detection/50000_entities_ecs__change_detection__Table 23.86 0.03
events_iter/size_16_events_10000 24.48 0.01
events_iter/size_4_events_10000 24.65 0.0
par_iter_simple/with_10_fragment 24.75 0.01
events_iter/size_4_events_50000 24.9 0.0
events_iter/size_4_events_1000 25.0 0.01
events_iter/size_16_events_100 26.74 0.01
multiple_archetypes_none_changed_detection/5_archetypes_100_entities_ecs__change_detection__Table 27.48 0.04
multiple_archetypes_none_changed_detection/100_archetypes_100_entities_ecs__change_detection__Table 31.58 0.01
multiple_archetypes_none_changed_detection/100_archetypes_1000_entities_ecs__change_detection__Table 44.78 0.03
none_changed_detection/5000_entities_ecs__change_detection__Table 46.4 0.01
none_changed_detection/50000_entities_ecs__change_detection__Table 46.96 0.03
multiple_archetypes_none_changed_detection/20_archetypes_100_entities_ecs__change_detection__Table 48.97 0.05
multiple_archetypes_none_changed_detection/20_archetypes_10000_entities_ecs__change_detection__Table 54.76 0.01
multiple_archetypes_none_changed_detection/100_archetypes_10000_entities_ecs__change_detection__Table 57.3 0.0
multiple_archetypes_none_changed_detection/5_archetypes_10000_entities_ecs__change_detection__Table 60.27 0.01
multiple_archetypes_none_changed_detection/5_archetypes_1000_entities_ecs__change_detection__Table 61.96 0.02
multiple_archetypes_none_changed_detection/20_archetypes_1000_entities_ecs__change_detection__Table 62.23 0.02

@Trashtalk217 Trashtalk217 added A-ECS Entities, components, systems, and events C-Performance A change motivated by improving speed, memory usage or compile times S-Needs-Review Needs reviewer attention (from anyone!) to move forward labels May 3, 2025
@hukasu
Copy link
Contributor

hukasu commented May 3, 2025

how often is a new item on Components added?

@Trashtalk217
Copy link
Contributor Author

@hukasu Only when a component is added. I don't quite know the stats for an average bevy game, but with a component count of 500 (which I think is on the high end), 500 times.

@hukasu
Copy link
Contributor

hukasu commented May 3, 2025

i'm running locally tests to see the times with BTreeMap, and Vec using binary_search and insert

Copy link
Contributor

@ElliottjPierce ElliottjPierce left a comment

Choose a reason for hiding this comment

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

Implementation looks good to me! The performance is really hard to justify at the moment IMO. I do want this, and I do think this is a good implementation, but I think we should work on caching component id where possible before merging this.

We should also look into other options. Since the component id is still dense for now, can we try a specialized hash function? We have one for Entity in the long run. The hashmap is a good move long term. We just need caching and a better hash function.

BTW, I'm cooking up better caching for queries ATM. Should be able to skip all component maps for queries in my upcoming PR.

IMO, divide and conquer between benching different map types and finding creative ways to cache and skip maps altogether. Then merge this (because it really does look good.)

@copygirl
Copy link
Contributor

copygirl commented May 3, 2025

Is flecs' approach of having the equivalent of a [Option<ComponentInfo>; 256] for low-id (commonly used) components useful in this case?

@ElliottjPierce
Copy link
Contributor

Is flecs' approach of having the equivalent of a [Option<ComponentInfo>; 256] for low-id (commonly used) components useful in this case?

Yes, but IMO, that's an optimization to look at after components as entities. We need "components can be totally sparse" (which that wouldn't help with), -> Component ids are entities -> Optimize entity hashmap. (IMO)

@hukasu
Copy link
Contributor

hukasu commented May 3, 2025

i've ran locally the benches 5 times now, and i have not see regressions as the ones shown here, i think the highest regression using BTreeMap was 40%, i also ran using Vec<ComponentKeyValue> (which is just a tuple with ComponentId and ComponentInfo) and using binary_search and insert and the change was within the same ball park, even Vec<ComponentKeyValue> and initialized with 512 capacity didn't change that much

i also saved the criterion reports but each zip is 33mb

@ElliottjPierce
Copy link
Contributor

Just putting it out there that with our currently dense ids and few components in benchmarks, the hybrid storage will be effectively just what we have today (from benchmark perspective).

@hukasu Could you run critcmp -5 or something so we can get an overview? https://github.com/BurntSushi/critcmp

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
A-ECS Entities, components, systems, and events C-Performance A change motivated by improving speed, memory usage or compile times S-Needs-Review Needs reviewer attention (from anyone!) to move forward
Projects
None yet
Development

Successfully merging this pull request may close these issues.

4 participants