// Copyright (c) the JPEG XL Project Authors. All rights reserved. // // Use of this source code is governed by a BSD-style // license that can be found in the LICENSE file.
// Block context used for scanning order, number of non-zeros, AC coefficients. // Equal to the channel.
constexpr uint32_t kDCTOrderContextStart = 0;
// The number of predicted nonzeros goes from 0 to 1008. We use // ceil(log2(predicted+1)) as a context for the number of nonzeros, so from 0 to // 10, inclusive.
constexpr uint32_t kNonZeroBuckets = 37;
// Supremum of ZeroDensityContext(x, y) + 1, when x + y < 64.
constexpr int kZeroDensityContextCount = 458; // Supremum of ZeroDensityContext(x, y) + 1.
constexpr int kZeroDensityContextLimit = 474;
/* This function is used for entropy-sources pre-clustering. * * Ideally, each combination of |nonzeros_left| and |k| should go to its own * bucket; but it implies (64 * 63 / 2) == 2016 buckets. If there is other * dimension (e.g. block context), then number of primary clusters becomes too * big. * * To solve this problem, |nonzeros_left| and |k| values are clustered. It is * known that their sum is at most 64, consequently, the total number buckets * is at most A(64) * B(64).
*/ // TODO(user): investigate, why disabling pre-clustering makes entropy code // less dense. Perhaps we would need to add HQ clustering algorithm that would // be able to squeeze better by spending more CPU cycles. static JXL_INLINE size_t ZeroDensityContext(size_t nonzeros_left, size_t k,
size_t covered_blocks,
size_t log2_covered_blocks,
size_t prev) {
JXL_DASSERT((static_cast<size_t>(1) << log2_covered_blocks) ==
covered_blocks);
nonzeros_left = (nonzeros_left + covered_blocks - 1) >> log2_covered_blocks;
k >>= log2_covered_blocks;
JXL_DASSERT(k > 0);
JXL_DASSERT(k < 64);
JXL_DASSERT(nonzeros_left > 0); // Asserting nonzeros_left + k < 65 here causes crashes in debug mode with // invalid input, since the (hot) decoding loop does not check this condition. // As no out-of-bound memory reads are issued even if that condition is // broken, we check this simpler condition which holds anyway. The decoder // will still mark a file in which that condition happens as not valid at the // end of the decoding loop, as `nzeros` will not be `0`.
JXL_DASSERT(nonzeros_left < 64); return (kCoeffNumNonzeroContext[nonzeros_left] + kCoeffFreqContext[k]) * 2 +
prev;
}
size_t Context(int dc_idx, uint32_t qf, size_t ord, size_t c) const {
size_t qf_idx = 0; for (uint32_t t : qf_thresholds) { if (qf > t) qf_idx++;
}
size_t idx = c < 2 ? c ^ 1 : 2;
idx = idx * kNumOrders + ord;
idx = idx * (qf_thresholds.size() + 1) + qf_idx;
idx = idx * num_dc_ctxs + dc_idx; return ctx_map[idx];
} // Non-zero context is based on number of non-zeros and block context. // For better clustering, contexts with same number of non-zeros are grouped.
constexpr uint32_t ZeroDensityContextsOffset(uint32_t block_ctx) const { returnstatic_cast<uint32_t>(num_ctxs * kNonZeroBuckets +
kZeroDensityContextCount * block_ctx);
}
// Context map for AC coefficients consists of 2 blocks: // |num_ctxs x : context for number of non-zeros in the block // kNonZeroBuckets| computed from block context and predicted // value (based top and left values) // |num_ctxs x : context for AC coefficient symbols, // kZeroDensityContextCount| computed from block context, // number of non-zeros left and // index in scan order
constexpr uint32_t NumACContexts() const { returnstatic_cast<uint32_t>(num_ctxs *
(kNonZeroBuckets + kZeroDensityContextCount));
}
// Non-zero context is based on number of non-zeros and block context. // For better clustering, contexts with same number of non-zeros are grouped. inline uint32_t NonZeroContext(uint32_t non_zeros, uint32_t block_ctx) const {
uint32_t ctx; if (non_zeros >= 64) non_zeros = 64; if (non_zeros < 8) {
ctx = non_zeros;
} else {
ctx = 4 + non_zeros / 2;
} returnstatic_cast<uint32_t>(ctx * num_ctxs + block_ctx);
}
Die Informationen auf dieser Webseite wurden
nach bestem Wissen sorgfältig zusammengestellt. Es wird jedoch weder Vollständigkeit, noch Richtigkeit,
noch Qualität der bereit gestellten Informationen zugesichert.
Bemerkung:
Die farbliche Syntaxdarstellung und die Messung sind noch experimentell.