Commit f384e4f
authored
perf(c++): optimize primitive struct fields read performance (#2960)
## Why?
<!-- Describe the purpose of this PR. -->
## What does this PR do?
1. Type-based encoding detection: Added compile-time helpers to
correctly distinguish signed (varint) vs unsigned (fixed) integers:
- field_is_fixed_primitive<Index>() - bool, int8, uint8, int16, uint16,
uint32, uint64, float, double
- field_is_varint_primitive<Index>() - int32_t, int, int64_t, long long
(zigzag varint)
2. Optimized fixed field reading:
- Compute field offsets at compile time with
compute_fixed_field_offset<T, I>()
- Read all fixed fields at absolute offsets without per-field
reader_index updates
- Single reader_index update after all fixed fields
3. Optimized varint field reading:
- Track offset locally during batch reading
- Removed overly conservative max-varint-bytes pre-check (varints are
variable-length)
- Single reader_index update after all varints
4. Three-phase deserialization:
- Phase 1: Batch read leading fixed-size primitives
- Phase 2: Batch read consecutive varint primitives
- Phase 3: Read remaining fields normally
## Related issues
#2958
#2906
## Does this PR introduce any user-facing change?
<!--
If any user-facing interface changes, please [open an
issue](https://github.com/apache/fory/issues/new/choose) describing the
need to do so and update the document if necessary.
Delete section if not applicable.
-->
- [ ] Does this PR introduce any public API change?
- [ ] Does this PR introduce any binary protocol compatibility change?
## Benchmark
| Datatype | Operation | Fory (ns) | Protobuf (ns) | Faster |
|----------|-----------|-----------|---------------|--------|
| Sample | Serialize | 103.9 | 59.2 | Protobuf (1.8x) |
| Sample | Deserialize | 329.3 | 478.1 | Fory (1.5x) |
| Struct | Serialize | 10.3 | 20.1 | Fory (1.9x) |
| Struct | Deserialize | 19.1 | 16.0 | Protobuf (1.2x) |1 parent 5cba6e5 commit f384e4f
1 file changed
+619
-102
lines changed
0 commit comments