Skip to content

Instantly share code, notes, and snippets.

@MurageKibicho
Created October 11, 2025 08:58
Show Gist options
  • Save MurageKibicho/27719ff900d8009d1adcca58dcf1e3d9 to your computer and use it in GitHub Desktop.
Save MurageKibicho/27719ff900d8009d1adcca58dcf1e3d9 to your computer and use it in GitHub Desktop.
In
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <limits.h>
#include <stdint.h>
#include <assert.h>
#include <math.h>
uint32_t RANGE_LOW = 1;
uint32_t RANGE_HIGH = 0xffffffff;
uint32_t RANGE_CURRENT = 0;
void ResetGlobalVariables()
{
RANGE_LOW = 1;
RANGE_HIGH = 0xffffffff;
RANGE_CURRENT = 0;
}
void EncodeToFile(int bit, float probability, FILE *fr)
{
assert(probability >= 0.0f);
assert(probability <= 1.0f);
assert(bit == 0 || bit == 1);
if(RANGE_HIGH < RANGE_LOW)
{
printf("%d %.3f\n",bit, probability);
}
assert(RANGE_HIGH > RANGE_LOW);
assert(RANGE_LOW >= 0);
unsigned char byte = 0;
int intProbability = (int) (probability * 65536.0f);
uint32_t RANGE_MID = RANGE_LOW +((RANGE_HIGH - RANGE_LOW) >> 16) * intProbability + ((((RANGE_HIGH - RANGE_LOW) & 0xffff) * intProbability) >> 16);
assert(RANGE_HIGH >= RANGE_MID);
assert(RANGE_MID >= RANGE_LOW);
if(bit){RANGE_HIGH = RANGE_MID;}else{RANGE_LOW = RANGE_MID + 1;}
while((RANGE_HIGH ^ RANGE_LOW) < 0x1000000)
{
byte = RANGE_HIGH >> 24;
fwrite(&byte, sizeof(byte), 1, fr);
RANGE_HIGH = RANGE_HIGH <<8 | 255;
RANGE_LOW = RANGE_LOW << 8;
}
}
void FlushEncoderToFile(FILE *fr)
{
unsigned char byte = 0;
uint32_t RANGE_MID = RANGE_HIGH;
for(int i = 3; i >= 0; i--)
{
byte = (RANGE_MID >> (8*i)) & 0xff;
fwrite(&byte, sizeof(byte), 1, fr);
}
}
int Decode(float probability, int characterLength, unsigned char *characters, size_t *characterIndex)
{
assert(probability >= 0.0f);assert(probability <= 1.0f);assert(RANGE_HIGH > RANGE_LOW);assert(RANGE_LOW >= 0);
int intProbability = (int) (probability * 65536.0f);
uint32_t RANGE_MID = RANGE_LOW +((RANGE_HIGH - RANGE_LOW) >> 16) * intProbability + ((((RANGE_HIGH - RANGE_LOW) & 0xffff) * intProbability) >> 16);
assert(RANGE_HIGH >= RANGE_MID);
assert(RANGE_MID >= RANGE_LOW);
int bit = RANGE_CURRENT <= RANGE_MID;
if(bit){RANGE_HIGH = RANGE_MID;}else{RANGE_LOW = RANGE_MID + 1;}
while((RANGE_HIGH ^ RANGE_LOW) < 0x1000000)
{
RANGE_HIGH = RANGE_HIGH << 8 | 255;
RANGE_LOW = RANGE_LOW << 8;
if(*characterIndex < characterLength-1)
{
assert(characters[*characterIndex] > -1);assert(characters[*characterIndex] < 256);
RANGE_CURRENT=RANGE_CURRENT<<8|characters[*characterIndex];
*characterIndex += 1;
}
else
{
assert(characters[*characterIndex] > -1);assert(characters[*characterIndex] < 256);
RANGE_CURRENT=RANGE_CURRENT<<8|characters[*characterIndex];
}
}
return bit;
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment