?? arcode.c
字號:
ar->Low = (ar->Low<<1);
ar->High = (ar->High<<1) + 1;
}
}
/*--------------------------------------------------------------------------------------------*/
/*--------------------------------------------------------------------------------------------*/
void AREncoderOpenFile(AREncoder *ar, char *filename)
{
if (!ar->Closed){
ARCoderError("File already opened.");
}
ar->f = fopen(filename, "wb");
if (ar->f == NULL){
ARCoderError("Fail to open file");
}
ar->Closed = 0;
ar->ByteCounter = 0;
ar->SymbolCounter = ar->Low = ar->BitsToFollow = ar->BitBuffer = 0;
ar->BitIndex = 8;
ar->High = TopValue;
return;
}
/*--------------------------------------------------------------------------------------------*/
/*--------------------------------------------------------------------------------------------*/
void AREncoderOpenAppendFile(AREncoder *ar, char * filename)
{
if (!ar->Closed){
ARCoderError("File already opened.");
}
ar->f = fopen(filename, "a+b");
if (ar->f == NULL){
ARCoderError("Fail to open file");
}
ar->Closed = 0;
ar->ByteCounter = 0;
ar->SymbolCounter = ar->Low = ar->BitsToFollow = ar->BitBuffer = ar->Closed = 0;
ar->BitIndex = 8;
ar->High = TopValue;
return;
}
/*--------------------------------------------------------------------------------------------*/
/*--------------------------------------------------------------------------------------------*/
void AREncoderCloseFile(AREncoder *ar)
{
if (ar->Closed){
return;
}
AREncoderFlush(ar);
if (fclose(ar->f)==EOF){
ARCoderError("Fail to close.");
}
ar->Closed = 1;
}
/*--------------------------------------------------------------------------------------------*/
/*--------------------------------------------------------------------------------------------*/
void AREncoderFlush(AREncoder *ar)
{
if (ar->Closed){
return;
}
ar->BitsToFollow++;
AREncoderBitPlusFollow(ar, ar->Low >= FirstQtr);
//if (ar->BitIndex<8){
if (putc(ar->BitBuffer >> ar->BitIndex, ar->f) == EOF){
ARCoderError("Fail to write.");
}
ar->ByteCounter++;
//}
return;
}
/*--------------------------------------------------------------------------------------------*/
/*--------------------------------------------------------------------------------------------*/
void AREncoderEncodeBit(AREncoder *ar, int bit)
{
long lm1 = ar->Low-1;
long range = ar->High-lm1;
if (bit){
ar->Low += (range >> 1);
}
else{
ar->High = lm1 +(range>>1);
}
AREncoderUpdateInterval(ar);
return;
}
/*--------------------------------------------------------------------------------------------*/
/*--------------------------------------------------------------------------------------------*/
void AREncoderEncodeSymbol(AREncoder *ar, int bit, HistoBi *h)
{
long lm1 = ar->Low -1;
long range = (ar->High-lm1) * h->c0 / (h->c0+h->c1);
if (bit){
ar->Low += range;
}
else{
ar->High = lm1 + range;
}
HistoBiUpdate(h, bit);
AREncoderUpdateInterval(ar);
return;
}
/*--------------------------------------------------------------------------------------------*/
/*--------------------------------------------------------------------------------------------*/
void AREncoderEncodeMSymbol(AREncoder *ar, int s, Histo *h)
{
long range = ar->High - ar->Low + 1;
long countLeft = HistoGetCumul(h, s-1);
long count = HistoGetCumul(h, s);
ar->High= ar->Low+(range*count)/h->TotalFreq - 1;
ar->Low = ar->Low+(range*countLeft)/h->TotalFreq;
HistoUpdate(h, 1, s);
AREncoderUpdateInterval(ar);
return;
}
/*--------------------------------------------------------------------------------------------*/
/*--------------------------------------------------------------------------------------------*/
void AREncoderEncodeBits(AREncoder *ar, int bits, int word)
{
int i, t;
unsigned int mask=1<<(bits-1);
for (i=bits-1; i>=0; i--){
t = (word & mask ? 1 : 0);
AREncoderEncodeBit(ar, (word & mask ? 1 : 0));
mask >>= 1;
}
}
/*--------------------------------------------------------------------------------------------*/
/*--------------------------------------------------------------------------------------------*/
int AREncoderBitsOutput(AREncoder *ar)
{
return (ar->ByteCounter<<3) + 10 + ar->BitsToFollow - ar->BitIndex;
}
/*--------------------------------------------------------------------------------------------*/
/*--------------------------------------------------------------------------------------------*/
AREncoder* AREncoderAlloc(void)
{
AREncoder *ar;
if ((ar=(AREncoder *)malloc(sizeof(AREncoder)))==NULL){
return NULL;
}
ar->Closed = 1;
return ar;
}
/*--------------------------------------------------------------------------------------------*/
/*--------------------------------------------------------------------------------------------*/
void AREncoderDealloc(AREncoder *ar)
{
if (!ar->Closed){
ARCoderWarning("File not closed.");
AREncoderCloseFile(ar);
}
free(ar);
}
/*--------------------------------------------------------------------------------------------*/
/*--------------------------------------------------------------------------------------------*/
/* Arithmetic Decoder Functions */
void ARDecoderInputByte(ARDecoder *ar)
{
if ((ar->BitBuffer = getc(ar->f)) == EOF){
if (++ar->ExtraBits > CodeValueBits - 2){
ARCoderError("End of file reached");
}
}
else{
ar->BitIndex = 8;
++ar->ByteCounter;
}
}
/*--------------------------------------------------------------------------------------------*/
/*--------------------------------------------------------------------------------------------*/
void ARDecoderUpdateInterval(ARDecoder *ar)
{
++ar->SymbolCounter;
for (;;){
if (ar->High < Half){
/* nothing */
}
else if (ar->Low >= Half) {
ar->Value -= Half;
ar->Low -= Half;
ar->High -= Half;
}
else if ((ar->Low >= FirstQtr) && (ar->High < ThirdQtr)){
ar->Value -= FirstQtr;
ar->Low -= FirstQtr;
ar->High -= FirstQtr;
}
else{
break;
}
ar->Low <<= 1;
ar->High += ar->High + 1;
ar->Value <<= 1;
if (!ar->BitIndex){
ARDecoderInputByte(ar);
}
if (ar->BitBuffer & 1){
ar->Value++;
}
ar->BitBuffer>>=1;
ar->BitIndex--;
}
}
/*--------------------------------------------------------------------------------------------*/
/*--------------------------------------------------------------------------------------------*/
void ARDecoderOpenFile(ARDecoder *ar, char* filename)
{
int i;
if (!ar->Closed){
ARCoderError("File already opened.");
}
ar->f = fopen(filename, "rb");
if (ar->f == NULL){
ARCoderError("Fail to open file");
}
ar->Closed = 0;
ar->ByteCounter = 0;
ar->SymbolCounter = ar->Low = ar->Value = ar->BitIndex = ar->ExtraBits = 0;
ar->High = TopValue;
for (i=0; i<CodeValueBits; i++){
if (!ar->BitIndex){
ARDecoderInputByte(ar);
}
ar->Value += ar->Value + (ar->BitBuffer & 1);
ar->BitBuffer >>=1;
ar->BitIndex--;
}
}
/*--------------------------------------------------------------------------------------------*/
/*--------------------------------------------------------------------------------------------*/
void ARDecoderOpenFileOffset(ARDecoder *ar, char* filename, int OffsetBytes)
{
int i;
if (!ar->Closed){
ARCoderError("File already opened.");
}
ar->f = fopen(filename, "rb");
if (ar->f == NULL){
ARCoderError("Fail to open file");
}
fseek(ar->f, OffsetBytes, SEEK_SET);
ar->Closed = 0;
ar->ByteCounter = 0;
ar->SymbolCounter = ar->Low = ar->Value = ar->BitIndex = ar->ExtraBits = 0;
ar->High = TopValue;
for (i=0; i<CodeValueBits; i++){
if (!ar->BitIndex){
ARDecoderInputByte(ar);
}
ar->Value += ar->Value + (ar->BitBuffer & 1);
ar->BitBuffer >>=1;
ar->BitIndex--;
}
}
/*--------------------------------------------------------------------------------------------*/
/*--------------------------------------------------------------------------------------------*/
void ARDecoderCloseFile(ARDecoder *ar)
{
if (ar->Closed){
return;
}
if (fclose(ar->f)==EOF){
ARCoderError("Fail to close.");
}
ar->Closed = 1;
}
/*--------------------------------------------------------------------------------------------*/
/*--------------------------------------------------------------------------------------------*/
int ARDecoderDecodeBit(ARDecoder *ar)
{
long lm1 = ar->Low - 1;
long range = ar->High - lm1;
int bit = (int) (((( ar->Value - lm1) << 1) - 1) / range);
if (bit){
ar->Low += (range >> 1);
}
else{
ar->High = lm1 + (range >> 1);
}
ARDecoderUpdateInterval(ar);
return bit;
}
/*--------------------------------------------------------------------------------------------*/
/*--------------------------------------------------------------------------------------------*/
int ARDecoderDecodeSymbol(ARDecoder *ar, HistoBi *h)
{
long lm1 = ar->Low - 1;
long range = ar->High - lm1;
int cum = (int)(((ar->Value - lm1) * (h->c0+h->c1) - 1) / range);
int bit = (cum >= h->c0);
range = range * h->c0 / (h->c0+h->c1);
if (bit){
ar->Low += range;
}
else{
ar->High = lm1 + range;
}
HistoBiUpdate(h, bit);
ARDecoderUpdateInterval(ar);
return bit;
}
/*--------------------------------------------------------------------------------------------*/
/*--------------------------------------------------------------------------------------------*/
int ARDecoderDecodeMSymbol(ARDecoder *ar, Histo *h)
{
long range, target, countLeft, count;
int s;
range = ar->High - ar->Low + 1;
target = ((int)(ar->Value-ar->Low+1)*h->TotalFreq-1)/(range);
s = HistoGetSymbol(h, target);
countLeft = HistoGetCumul(h, s-1);
count = HistoGetCumul(h, s);
ar->High = ar->Low+(range*count)/h->TotalFreq-1;
ar->Low = ar->Low+(range*countLeft)/h->TotalFreq;
HistoUpdate(h, 1, s);
ARDecoderUpdateInterval(ar);
return s;
}
/*--------------------------------------------------------------------------------------------*/
/*--------------------------------------------------------------------------------------------*/
int ARDecoderDecodeBits(ARDecoder *ar, int bits)
{
int val=0, i;
for (i=bits-1; i>=0; i--){
val = (val<<1) + ARDecoderDecodeBit(ar);
}
return val;
}
/*--------------------------------------------------------------------------------------------*/
/*--------------------------------------------------------------------------------------------*/
int ARDecoderBitsInput(ARDecoder *ar)
{
return (ar->ByteCounter<<3) - ar->BitIndex + 8;
}
/*--------------------------------------------------------------------------------------------*/
/*--------------------------------------------------------------------------------------------*/
ARDecoder* ARDecoderAlloc(void)
{
ARDecoder *ar;
if ((ar=(ARDecoder *)malloc(sizeof(ARDecoder)))==NULL){
return NULL;
}
ar->Closed = 1;
return ar;
}
/*--------------------------------------------------------------------------------------------*/
/*--------------------------------------------------------------------------------------------*/
void ARDecoderDealloc(ARDecoder *ar)
{
if (!ar->Closed){
ARCoderWarning("File not closed.");
ARDecoderCloseFile(ar);
}
free(ar);
}
/*--------------------------------------------------------------------------------------------*/
/*--------------------------------------------------------------------------------------------*/
void ARCoderWarning(char *fmt, ...)
{
va_list argptr;
va_start( argptr, fmt );
printf( "ARCoderWarning: " );
vprintf( fmt, argptr );
va_end( argptr );
exit( -1 );
}
/*--------------------------------------------------------------------------------------------*/
/*--------------------------------------------------------------------------------------------*/
void ARCoderError(char *fmt, ...)
{
va_list argptr;
va_start( argptr, fmt );
printf( "ARCoderError: " );
vprintf( fmt, argptr );
va_end( argptr );
exit( -1 );
}
/*--------------------------------------------------------------------------------------------*/
/*--------------------------------------------------------------------------------------------*/
?? 快捷鍵說明
復制代碼
Ctrl + C
搜索代碼
Ctrl + F
全屏模式
F11
切換主題
Ctrl + Shift + D
顯示快捷鍵
?
增大字號
Ctrl + =
減小字號
Ctrl + -