⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 cdfpred.c

📁 一个简单而且快速的无损压缩算法。包含源代码实现
💻 C
📖 第 1 页 / 共 2 页
字号:
#include "cdftypes.h"
#include "cdfpred.h"
#include "bppmask.h"
#include "assert.h"
#include <memory.h>


/* zwroc mediane */
#define MEDIAN(A, B, C)								\
		( (B)>=(C) ?								\
		  (C)>=(A) ? (C) : (A)>=(B) ? (B) : (A) :	\
		  (C)<=(A) ? (C) : (A)<=(B) ? (B) : (A)		\
		)											\


/* automatyczne tlumaczenie rozkladu U na L, wypelniane przez decorelateinit() dla 8bpp i mniej*/
static unsigned int xlatU2L[256]; 


/* kompresja kodu zrodlowego */
#define PIXEL_A ((unsigned int)currow[i-1])
#define PIXEL_B ((unsigned int)prevrow[i])
#define PIXEL_C ((unsigned int)prevrow[i-1])


/* pomocnicze do dekorelowania pojedynczych pikseli */
/*  0  */
static void decorelate_onepixel_0(const PIXEL * const currow, PIXEL * const decorelatedrow, 
		    					  const unsigned int pixelbitmask)
{
	const unsigned int s=*currow; 
		
	if (s<=(pixelbitmask>>1)) 
		*decorelatedrow=s<<1; 
	else 
		*decorelatedrow=((pixelbitmask-s)<<1)+1; 
}


static void decorelate_onepixel_0_8bpp(const BYTE * const currow, BYTE * const decorelatedrow, 
		    						   const unsigned int pixelbitmask)
{
	const unsigned int s=*currow; 
		
	*decorelatedrow=xlatU2L[s];
}


static void decorelate_onepixel_2(const PIXEL * const prevrow, const PIXEL * const currow, 
								  PIXEL * const decorelatedrow, const unsigned int pixelbitmask)
{
	const unsigned int s=(unsigned)( (int)(*currow) - (int)(*prevrow) ) & pixelbitmask; 
		
	if (s<=(pixelbitmask>>1)) 
		*decorelatedrow=s<<1; 
	else 
		*decorelatedrow=((pixelbitmask-s)<<1)+1; 
}


static void decorelate_onepixel_2_8bpp(const BYTE * const prevrow, const BYTE * const currow, 
									   BYTE * const decorelatedrow, const unsigned int pixelbitmask)
{
	const unsigned int s=(unsigned)( (int)(*currow) - (int)(*prevrow) ) & pixelbitmask; 
		
	*decorelatedrow=xlatU2L[s];
}


/* dekorelowanie calych wierszy */


/*  0  */
static void decorelate_0(const PIXEL currow[], const unsigned int rowlen, const int bpp,
						 PIXEL decorelatedrow[])
{
	const unsigned int pixelbitmask=bppmask[bpp];
	const unsigned int pixelbitmaskshr=pixelbitmask>>1;
	unsigned int i;

	for (i=0; i<rowlen; i++)
	{
		const unsigned int s=currow[i]; 
		
		if (s<=pixelbitmaskshr) 
			decorelatedrow[i]=s<<1; 
		else 
			decorelatedrow[i]=((pixelbitmask-s)<<1)+1; 
	}
}


static void decorelate_0_8bpp(const BYTE currow[], const unsigned int rowlen, const int bpp,
							  BYTE decorelatedrow[])
{
	const unsigned int pixelbitmask=bppmask[bpp];
	const unsigned int pixelbitmaskshr=pixelbitmask>>1;
	unsigned int i;

	for (i=0; i<rowlen; i++)
	{
		const unsigned int s=currow[i]; 
		
		decorelatedrow[i]=xlatU2L[s];
	}
}


/*  a  */
static void decorelate_1(const PIXEL currow[], const unsigned int rowlen, const int bpp,
						 PIXEL decorelatedrow[])
{
	const unsigned int pixelbitmask=bppmask[bpp];
	const unsigned int pixelbitmaskshr=pixelbitmask>>1;
	unsigned int i;

	assert(rowlen);	// osobne wywolanie dla pierwszego piksela, bo on nie ma lewego sasiada i komplikowalby ponizsza petle - nie daloby sie zrobic unrolling
	decorelate_onepixel_0(currow, decorelatedrow, pixelbitmask);
	for (i=1; i<rowlen; i++)
	{
		const unsigned int s=(unsigned)( (int)currow[i] - (int)PIXEL_A ) & pixelbitmask; 
		
		if (s<=pixelbitmaskshr) 
			decorelatedrow[i]=s<<1; 
		else 
			decorelatedrow[i]=((pixelbitmask-s)<<1)+1; 
	}
}


static void decorelate_1_8bpp(const BYTE currow[], const unsigned int rowlen, const int bpp,
							  BYTE decorelatedrow[])
{
	const unsigned int pixelbitmask=bppmask[bpp];
	const unsigned int pixelbitmaskshr=pixelbitmask>>1;
	unsigned int i;

	assert(rowlen);	// osobne wywolanie dla pierwszego piksela, bo on nie ma lewego sasiada i komplikowalby ponizsza petle - nie daloby sie zrobic unrolling
	decorelate_onepixel_0_8bpp(currow, decorelatedrow, pixelbitmask);
	for (i=1; i<rowlen; i++)
	{
		const unsigned int s=(unsigned)( (int)currow[i] - (int)PIXEL_A ) & pixelbitmask; 
		
		decorelatedrow[i]=xlatU2L[s];
	}
}


/*  b  */
static void decorelate_2(const PIXEL prevrow[], const PIXEL currow[], const unsigned int rowlen, const int bpp,
						 PIXEL decorelatedrow[])
{
	const unsigned int pixelbitmask=bppmask[bpp];
	const unsigned int pixelbitmaskshr=pixelbitmask>>1;
	unsigned int i;

	for (i=0; i<rowlen; i++)
	{
		const unsigned int s=(unsigned)( (int)currow[i] - (int)PIXEL_B ) & pixelbitmask; 
		
		if (s<=pixelbitmaskshr) 
			decorelatedrow[i]=s<<1; 
		else 
			decorelatedrow[i]=((pixelbitmask-s)<<1)+1; 
	}
}


static void decorelate_2_8bpp(const BYTE prevrow[], const BYTE currow[], const unsigned int rowlen, const int bpp,
							  BYTE decorelatedrow[])
{
	const unsigned int pixelbitmask=bppmask[bpp];
	const unsigned int pixelbitmaskshr=pixelbitmask>>1;
	unsigned int i;

	for (i=0; i<rowlen; i++)
	{
		const unsigned int s=(unsigned)( (int)currow[i] - (int)PIXEL_B ) & pixelbitmask; 
		
		decorelatedrow[i]=xlatU2L[s];
	}
}


/*  c  */
static void decorelate_3(const PIXEL prevrow[], const PIXEL currow[], const unsigned int rowlen, const int bpp,
						 PIXEL decorelatedrow[])
{
	const unsigned int pixelbitmask=bppmask[bpp];
	const unsigned int pixelbitmaskshr=pixelbitmask>>1;
	unsigned int i;

	assert(rowlen);	// osobne wywolanie dla pierwszego piksela, bo on nie ma lewego sasiada i komplikowalby ponizsza petle - nie daloby sie zrobic unrolling
	decorelate_onepixel_2(prevrow, currow, decorelatedrow, pixelbitmask);
	for (i=1; i<rowlen; i++)
	{
		const unsigned int s=(unsigned)( (int)currow[i] - (int)PIXEL_C ) & pixelbitmask; 
		
		if (s<=pixelbitmaskshr) 
			decorelatedrow[i]=s<<1; 
		else 
			decorelatedrow[i]=((pixelbitmask-s)<<1)+1; 
	}
}


static void decorelate_3_8bpp(const BYTE prevrow[], const BYTE currow[], const unsigned int rowlen, const int bpp,
							  BYTE decorelatedrow[])
{
	const unsigned int pixelbitmask=bppmask[bpp];
	const unsigned int pixelbitmaskshr=pixelbitmask>>1;
	unsigned int i;

	assert(rowlen);	// osobne wywolanie dla pierwszego piksela, bo on nie ma lewego sasiada i komplikowalby ponizsza petle - nie daloby sie zrobic unrolling
	decorelate_onepixel_2_8bpp(prevrow, currow, decorelatedrow, pixelbitmask);
	for (i=1; i<rowlen; i++)
	{
		const unsigned int s=(unsigned)( (int)currow[i] - (int)PIXEL_C ) & pixelbitmask; 
		
		decorelatedrow[i]=xlatU2L[s];
	}
}


/*  a+b-c  */
static void decorelate_4(const PIXEL prevrow[], const PIXEL currow[], const unsigned int rowlen, const int bpp,
						 PIXEL decorelatedrow[])
{
	const unsigned int pixelbitmask=bppmask[bpp];
	const unsigned int pixelbitmaskshr=pixelbitmask>>1;
	unsigned int i;

	assert(rowlen);	// osobne wywolanie dla pierwszego piksela, bo on nie ma lewego sasiada i komplikowalby ponizsza petle - nie daloby sie zrobic unrolling
	decorelate_onepixel_2(prevrow, currow, decorelatedrow, pixelbitmask);
	for (i=1; i<rowlen; i++)
	{
		int p=((int)(PIXEL_A+PIXEL_B) - (int)PIXEL_C);

		if (p<0)
			p=0;
		else if ((unsigned)p>pixelbitmask)
			p=pixelbitmask;

		{
			const unsigned int s=(unsigned)( (int)currow[i] - p ) & pixelbitmask; 
			
			if (s<=pixelbitmaskshr) 
				decorelatedrow[i]=s<<1; 
			else 
				decorelatedrow[i]=((pixelbitmask-s)<<1)+1; 
		}
	}
}


static void decorelate_4_8bpp(const BYTE prevrow[], const BYTE currow[], const unsigned int rowlen, const int bpp,
						      BYTE decorelatedrow[])
{
	const unsigned int pixelbitmask=bppmask[bpp];
	const unsigned int pixelbitmaskshr=pixelbitmask>>1;
	unsigned int i;

	assert(rowlen);	// osobne wywolanie dla pierwszego piksela, bo on nie ma lewego sasiada i komplikowalby ponizsza petle - nie daloby sie zrobic unrolling
	decorelate_onepixel_2_8bpp(prevrow, currow, decorelatedrow, pixelbitmask);
	for (i=1; i<rowlen; i++)
	{
		int p=((int)(PIXEL_A+PIXEL_B) - (int)PIXEL_C);

		if (p<0)
			p=0;
		else if ((unsigned)p>pixelbitmask)
			p=pixelbitmask;

		{
			const unsigned int s=(unsigned)( (int)currow[i] - p ) & pixelbitmask; 
			
			decorelatedrow[i]=xlatU2L[s];
		}
	}
}


/*  a+(b-c)/2  */
static void decorelate_5(const PIXEL prevrow[], const PIXEL currow[], const unsigned int rowlen, const int bpp,
						 PIXEL decorelatedrow[])
{
	const unsigned int pixelbitmask=bppmask[bpp];
	const unsigned int pixelbitmaskshr=pixelbitmask>>1;
	unsigned int i;

	assert(rowlen);	// osobne wywolanie dla pierwszego piksela, bo on nie ma lewego sasiada i komplikowalby ponizsza petle - nie daloby sie zrobic unrolling
	decorelate_onepixel_2(prevrow, currow, decorelatedrow, pixelbitmask);
	for (i=1; i<rowlen; i++)
	{
		int p=( (int)PIXEL_A + (((int)PIXEL_B-(int)PIXEL_C)>>1) ) ;

		if (p<0)
			p=0;
		else if ((unsigned)p>pixelbitmask)
			p=pixelbitmask;

		{
			const unsigned int s=(unsigned)( (int)currow[i] - p ) & pixelbitmask; 
			
			if (s<=pixelbitmaskshr) 
				decorelatedrow[i]=s<<1; 
			else 
				decorelatedrow[i]=((pixelbitmask-s)<<1)+1; 
		}
	}
}


static void decorelate_5_8bpp(const BYTE prevrow[], const BYTE currow[], const unsigned int rowlen, const int bpp,
							  BYTE decorelatedrow[])
{
	const unsigned int pixelbitmask=bppmask[bpp];
	const unsigned int pixelbitmaskshr=pixelbitmask>>1;
	unsigned int i;

	assert(rowlen);	// osobne wywolanie dla pierwszego piksela, bo on nie ma lewego sasiada i komplikowalby ponizsza petle - nie daloby sie zrobic unrolling
	decorelate_onepixel_2_8bpp(prevrow, currow, decorelatedrow, pixelbitmask);
	for (i=1; i<rowlen; i++)
	{
		int p=( (int)PIXEL_A + (((int)PIXEL_B-(int)PIXEL_C)>>1) ) ;

		if (p<0)
			p=0;
		else if ((unsigned)p>pixelbitmask)
			p=pixelbitmask;

		{
			const unsigned int s=(unsigned)( (int)currow[i] - p ) & pixelbitmask; 
			
			decorelatedrow[i]=xlatU2L[s];
		}
	}
}


/*  b+(a-c)/2  */
static void decorelate_6(const PIXEL prevrow[], const PIXEL currow[], const unsigned int rowlen, const int bpp,
						 PIXEL decorelatedrow[])
{
	const unsigned int pixelbitmask=bppmask[bpp];
	const unsigned int pixelbitmaskshr=pixelbitmask>>1;
	unsigned int i;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -