Refactor LZ-String implementation into modular core with platform abstraction (Qt + non-Qt support)#5
Open
vakarelov wants to merge 10 commits intoamiart:masterfrom
Open
Refactor LZ-String implementation into modular core with platform abstraction (Qt + non-Qt support)#5vakarelov wants to merge 10 commits intoamiart:masterfrom
vakarelov wants to merge 10 commits intoamiart:masterfrom
Conversation
The file defining the exec file
…pled block into a layered, extensible architecture while preserving the public API (LZString::{compress,compressToUTF16,compressToBase64,decompress,decompressFromUTF16,decompressFromBase64}).
Highlights:
Core / Algorithm Separation
Introduced LZCore to encapsulate compression and decompression logic.
LZString is now a thin façade delegating to LZCore, improving readability and testability.
Unified internal logic across normal, UTF-16, and Base64 variants by parameterizing bit width and output mapping.
Platform Abstraction
Added ILZPlatform interface to abstract string length, slicing, concatenation, character code translation, and output symbol mapping.
Implemented QtLZPlatform for QString-based builds.
Added optional StdLZPlatform (activated via LZSTRING_NO_QT) enabling use without Qt by typedefing QString to std::string.
Base64 alphabet and reverse lookup moved into platform objects with precomputed reverse maps.
Compression Path Improvements
Replaced ad hoc state handling with clearer local lambdas (writeBit, writeNBits).
Reduced duplication in emitting character codes (8-bit vs 16-bit paths) by passing a platform callback.
Preallocation heuristics retained (reserve based on input size) to minimize reallocations.
Dictionary and creation tracking now use std containers with explicit lifecycle.
Decompression Path Improvements
Rewrote bit reading using compact helpers (readBit, readNBits) for clarity.
Delegated source symbol acquisition to lambdas instead of multiple helper classes.
Maintains original dictionary growth semantics (enlargeIn / numBits) and special handling for dictSize edge cases.
Behavior & Compatibility
Public API unchanged; return values and edge case handling (empty input => empty output) preserved.
Base64 padding logic retained (appends '=', '==', or '===').
UTF-16 compressed form still appends a trailing space for compatibility.
Numeric bounds (reset values, bit widths) match established LZ-String logic; conditional adjustments for 8-bit vs 16-bit environments included.
Extensibility & Portability
Clear path for adding new output encodings or URI-safe Base64 variant.
Non-Qt builds now feasible without altering algorithm code.
Encapsulation enables future streaming or incremental APIs.
Maintainability
Concentrated algorithmic complexity inside LZCore with a smaller, stable external surface.
Removed repeated bit-flush sequences via reusable abstractions.
Improved naming and structure around dictionary operations and termination markers.
Performance Considerations
Fewer temporary string fragment objects (no substring view objects).
Precomputed Base64 reverse map avoids per-call reconstruction.
Structure now amenable to future switch from std::map to unordered_map if profiling justifies it.
Follow-up opportunities (not included here):
Add benchmark + regression tests comparing outputs against canonical vectors.
Introduce URI-safe Base64 variant.
Provide streaming compression/decompression APIs for large inputs.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
LZString Refactor Summary
This change restructures the implementation from a single tightly coupled block into a layered, extensible architecture while preserving the public API:
Public API:
LZString::{compress, compressToUTF16, compressToBase64, decompress, decompressFromUTF16, decompressFromBase64}Highlights
Core / Algorithm Separation
LZCoreto encapsulate compression and decompression logic.LZStringis now a thin façade delegating toLZCore, improving readability and testability.Platform Abstraction
ILZPlatforminterface to abstract string length, slicing, concatenation, character code translation, and output symbol mapping.QtLZPlatformforQString-based builds.StdLZPlatform(activated viaLZSTRING_NO_QT) enabling use without Qt by typedefingQStringtostd::string.Compression Path Improvements
writeBit,writeNBits).stdcontainers with explicit lifecycle.Decompression Path Improvements
readBit,readNBits) for clarity.enlargeIn,numBits) and special handling fordictSizeedge cases.Behavior & Compatibility
'=','==', or'===').Extensibility & Portability
Maintainability
LZCorewith a smaller, stable external surface.Performance Considerations
std::maptounordered_mapif profiling justifies it.Follow-up Opportunities (Not Included Here)