template <typename T, class M>
class PCdecoder<T, M, false> {
public:
PCdecoder(RCdecoder* rd, RCmodel*const* rm) : rd(rd), rm(rm) {}
~PCdecoder() {}
T decode(T pred, uint context = 0);
static const uint symbols = 2 * (1 << M::bits) - 1;
private:
static const uint bias = (1 << M::bits) - 1;
M map; RCdecoder*const rd; RCmodel*const* rm; };
template <typename T, class M>
T PCdecoder<T, M, false>::decode(T pred, uint context)
{
typedef typename M::Range U;
U p = map.forward(pred);
U r = p + rd->decode(rm[context]) - bias;
return map.inverse(r);
}
template <typename T, class M>
class PCdecoder<T, M, true> {
public:
PCdecoder(RCdecoder* rd, RCmodel*const* rm) : rd(rd), rm(rm) {}
~PCdecoder() {}
T decode(T pred, uint context = 0);
static const uint symbols = 2 * M::bits + 1;
private:
static const uint bias = M::bits;
M map; RCdecoder*const rd; RCmodel*const* rm; };
template <typename T, class M>
T PCdecoder<T, M, true>::decode(T pred, uint context)
{
typedef typename M::Range U;
uint s = rd->decode(rm[context]);
if (s > bias) { uint k = s - bias - 1;
U d = (U(1) << k) + rd->template decode<U>(k);
U p = map.forward(pred);
U r = p + d;
return map.inverse(r);
}
else if (s < bias) { uint k = bias - 1 - s;
U d = (U(1) << k) + rd->template decode<U>(k);
U p = map.forward(pred);
U r = p - d;
return map.inverse(r);
}
else return map.identity(pred);
}