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

📄 sadct.cpp

📁 完整的RTP RTSP代码库
💻 CPP
📖 第 1 页 / 共 3 页
字号:
/*************************************************************************This software module was originally developed by 	Stefan Rauthenberg (rauthenberg@HHI.DE), HHI	(date: January, 1998)in the course of development of the MPEG-4 Video (ISO/IEC 14496-2). This software module is an implementation of a part of one or more MPEG-4 Video tools as specified by the MPEG-4 Video. ISO/IEC gives users of the MPEG-4 Video free license to this software module or modifications thereof for use in hardware or software products claiming conformance to the MPEG-4 Video. Those intending to use this software module in hardware or software products are advised that its use may infringe existing patents. The original developer of this software module and his/her company, the subsequent editors and their companies, and ISO/IEC have no liability for use of this software module or modifications thereof in an implementation. Copyright is not released for non MPEG-4 Video conforming products. Microsoft retains full right to use the code for his/her own purpose, assign or donate the code to a third party and to inhibit third parties from using the code for non <MPEG standard> conforming products. This copyright notice must be included in all copies or derivative works. Copyright (c) 1998.Module Name:	sadct.cppAbstract:	SADCT and inverse SADCTRevision History:  *************************************************************************/#include "typeapi.h"#include "dct.hpp"#include <math.h>#if defined(__DEBUG_SADCT_) && !defined(NDEBUG)#include <iostream.h>#endif#ifdef __MFC_#ifdef _DEBUG#undef THIS_FILEstatic char BASED_CODE THIS_FILE[] = __FILE__;#endif#define new DEBUG_NEW				   #endif // __MFC_CSADCT::CSADCT():	m_N(8),	m_mat_tmp1(0),	m_row_buf(0),	m_ly(0),	m_lx(0),	m_mask(0){	allocMatrix(&m_mat_tmp1, m_N, m_N);		m_row_buf = new Float[m_N];	m_ly = new Int[m_N];	m_lx = new Int[m_N];		allocMatrix(&m_mask, m_N, m_N);		allocMatrix(&m_in, m_N, m_N);	allocMatrix(&m_out, m_N, m_N);	// Schueuer HHI: added for fast_sadct#ifdef _FAST_SADCT_	c_buf = new Float[m_N];	allocMatrix(&tmp_out, m_N, m_N);	f0_2 = 0.707107;	f0_3 = 0.577350;	f1_3 = 0.707107;	f2_3 = 0.408248;	f3_3 = 0.816497;	f0_4 = 0.500000;	f1_4 = 0.653281;	f2_4 = 0.270598;	f0_5 = 0.447214;	f1_5 = 0.601501;	f2_5 = 0.371748;	f3_5 = 0.511667;	f4_5 = 0.195440;	f5_5 = 0.632456;	f0_6 = 0.408248;	f1_6 = 0.557678;	f2_6 = 0.500000; 	f3_6 = 0.288675;	f4_6 = 0.149429;	f5_6 = 0.577350;	f0_7 = 0.377964;	f1_7 = 0.521121;	f2_7 = 0.481588; 	f3_7 = 0.417907;	f4_7 = 0.333269;	f5_7 = 0.231921;	f6_7 = 0.118942;	f7_7 = 0.534522;	f0_8 = 0.7071068;	f1_8 = 0.4903926;	f2_8 = 0.4619398;	f3_8 = 0.4157348;	f4_8 = 0.3535534;	f5_8 = 0.2777851;	f6_8 = 0.1913417;	f7_8 = 0.0975452;	sq[0] = 0.00000000000;	sq[1] = 1.00000000000;	sq[2] =	1.41421356237;	sq[3] =	1.73205080757;	sq[4] =	2.00000000000;	sq[5] =	2.23606797750;	sq[6] =	2.44948974278;	sq[7] =	2.64575131106;	sq[8] =	2.82842712475;#endif}CSADCT::~CSADCT(){	freeMatrix(m_mat_tmp1, m_N);	delete [] m_row_buf;	delete [] m_ly;	delete [] m_lx;	freeMatrix(m_mask, m_N);		freeMatrix(m_in, m_N);	freeMatrix(m_out, m_N);// Schueuer HHI #ifdef _FAST_SADCT_	delete [] c_buf;	freeMatrix(tmp_out, m_N);#endif}Void CSADCT::allocMatrix(Float ***mat, Int nr, Int nc) {	Float **m = new Float* [nr];	m[0] = new Float[nr*nc];		for (Int i=1; i<nr; i++) {		m[i] = m[i-1] + nc;	}	*mat = m;}Void CSADCT::allocMatrix(PixelC ***mat, Int nr, Int nc) {	PixelC **m = new PixelC* [nr];	m[0] = new PixelC[nr*nc];		for (Int i=1; i<nr; i++) {		m[i] = m[i-1] + nc;	}	*mat = m;}Float ***CSADCT::allocDctTable(Int n) {	Float ***tbl = new Float** [n+1];	tbl[0] = 0;		// transformation length of zero is impossible			for (Int i=1; i<=n; i++) {		allocMatrix(&tbl[i], n, n);	}		return (tbl);}Float ***CInvSADCT::allocReorderTable(Int n){	Float ***tbl = new Float** [n];		for (Int i=0; i<n; i++) {		tbl[i] = new Float* [n];		// to play it safe and get an exception if trying to access		// an uninitialized poInter.		memset(tbl[i], 0, sizeof(Float*)*n);	}	return tbl;}Void CInvSADCT::freeReorderTable(Float ***tbl, Int n){		if (tbl) {		for (Int i=0; i<n; i++)			delete [] tbl[i];		delete [] tbl;	}}// parameter nr not used yet because the data elements are allocated in contiguous memory and // in separate rows.Void CSADCT::freeMatrix(Float **mat, Int nr) {	if (mat) {		delete [] mat[0];		delete [] mat;	}}Void CSADCT::freeMatrix(PixelC **mat, Int nr) {	if (mat) {		delete [] mat[0];		delete [] mat;	}}Void CSADCT::freeDctTable(Float ***tbl, Int n) {	if (tbl) {		for (Int i=1; i<=n; i++) {			freeMatrix(tbl[i], n);		} 		delete [] tbl;	}}Void CSADCT::getRowLength(Int *lx, const PixelC* ppxlcMask, Int iStride){	prepareMask(ppxlcMask, iStride);	getRowLengthInternal(lx, m_mask, m_N, m_N);}/* *	returns in `lx' the number of active pels per line after shifting *	the pels towards the upper left corner.  This function may be *	called by a decoder in order to find out how the pels of a partial *	block are arranged for transmission.   */Void CSADCT::getRowLengthInternal(Int *lx, PixelC **mask, Int bky, Int bkx){	Int iy_out = 0;	Int iy, ix, l;		for (ix=0; ix<bkx; ix++) {		l = 0;		for (iy=0; iy<bky; iy++) {			if ( mask[iy][ix] ) 				l++;		}		if ( l ) 			m_ly[iy_out++] = l;	}		for (ix=iy_out; ix<bkx; ix++) 		m_ly[ix] = 0;		for (iy=0; iy<bky; iy++) {		l = 0;		for (ix=0; ix<bkx; ix++) {			if ( m_ly[ix] > iy )				l++;		}		lx[iy] = l;	}	}Void CSADCT::prepareMask(const PixelC* rgchMask, Int stride){	for (Int iy=0; iy<m_N; iy++) {    	PixelC* dstPtr = m_mask[iy];        const PixelC* srcPtr = rgchMask;        for (Int ix=0; ix<m_N; ix++)         	*dstPtr++ = (*srcPtr++ != transpValue) ? 1 : 0;                    		rgchMask += stride;	}}Void CSADCT::prepareInputBlock(Float **matDst, const Int *rgiSrc, Int stride){	Float *rowDstPtr;	const Int *rowSrcPtr;		for (Int iy=0; iy<m_N; iy++) {		rowDstPtr = matDst[iy];		rowSrcPtr = rgiSrc + iy*stride;		for (Int ix=0; ix<m_N; ix++) {			*rowDstPtr++ = *rowSrcPtr++;		}	}}Void CSADCT::prepareInputBlock(Float **matDst, const PixelC *rgiSrc, Int stride){	Float *rowDstPtr;	const PixelC *rowSrcPtr;	for (Int iy=0; iy<m_N; iy++) {		rowDstPtr = matDst[iy];		rowSrcPtr = rgiSrc + iy*stride;		for (Int ix=0; ix<m_N; ix++) {			*rowDstPtr++ = *rowSrcPtr++;		}	}}CFwdSADCT::CFwdSADCT(UInt nBits) :	CFwdBlockDCT(nBits){	m_dct_matrix = allocDctTable(m_N);	initTrfTables();}CFwdSADCT::~CFwdSADCT(){	freeDctTable(m_dct_matrix, m_N);}Void CFwdSADCT::initTrfTables(Float scale){	Float **mat, a, factcos;	Int u, x;	Int n;		for (n=1; n<=m_N; n++) {		mat = m_dct_matrix[n];		factcos = M_PI/(2*n);		a = scale * sqrt(2.0 / n);   		for (u=0; u<n; u++) {			for (x=0; x<n; x++) {				mat[u][x] = a * cos(factcos*u*(2*x+1));				if ( u == 0 )					mat[u][x] /= M_SQRT2;			}		}	}}// shape adaptive dct for inter coded blocks.Void CFwdSADCT::apply(const Int* rgiSrc, Int nColSrc, Int* rgiDst, Int nColDst, const PixelC* rgchMask, Int nColMask, Int *lx){	if (rgchMask) {		prepareMask(rgchMask, nColMask);		prepareInputBlock(m_in, rgiSrc, nColSrc);// Schueuer HHI: added for fast_sadct#ifdef _FAST_SADCT_		fast_transform(m_out, lx, m_in, m_mask, m_N, m_N);#else		transform(m_out, lx, m_in, m_mask, m_N, m_N);#endif		copyBack(rgiDst, nColDst, m_out, lx);	}	else		CBlockDCT::apply(rgiSrc, nColSrc, rgiDst, nColDst, NULL, 0, NULL);}// inverse shape adaptive dct for intra coded blocks.Void CFwdSADCT::apply (const PixelC* rgchSrc, Int nColSrc, Int* rgiDst, Int nColDst, const PixelC* rgchMask, Int nColMask, Int *lx){	if (rgchMask) {		prepareMask(rgchMask, nColMask);		prepareInputBlock(m_in, rgchSrc, nColSrc);// HHI Schueuer: inserted for fastsadct#ifdef _FAST_SADCT_		fast_deltaDCTransform(m_out, lx, m_in, m_mask, m_N, m_N);	#else		deltaDCTransform(m_out, lx, m_in, m_mask, m_N, m_N);#endif		// dirty hack for the AC/DC prediction: The transparent pixels of the        // first row and columns must be cleared acc. to the sadct proposal.        memset(rgiDst, 0, m_N*sizeof(PixelI));        PixelI* rgiDstPtr = rgiDst+nColDst;        for (int i = 1; i < m_N; i++ ) {        	*rgiDstPtr = 0;            rgiDstPtr += nColDst;        }       		copyBack(rgiDst, nColDst, m_out, lx);	}	else 		CBlockDCT::apply(rgchSrc, nColSrc, rgiDst, nColDst, NULL, 0, NULL);}Void CFwdSADCT::copyBack(PixelI *rgiDst, Int nColDst, Float **in, Int *lx){	Float *rowSrcPtr;	PixelI *rowDstPtr;	int i, j;		for (i=0; i<m_N && lx[i]; i++) {		rowSrcPtr = in[i];		rowDstPtr = rgiDst;		for (j = 0; j < lx[i]; j++) { 			*rowDstPtr = (*rowSrcPtr < 0) ? (PixelI)(*rowSrcPtr - .5) :			(PixelI)(*rowSrcPtr + .5);			rowDstPtr++;			rowSrcPtr++;		}		rgiDst += nColDst;	}}Void CFwdSADCT::deltaDCTransform(Float **out, Int *lx, Float **in, PixelC **mask, Int bky, Int bkx){	Int i, j;	Float mean_value;	Int active_pels;	out[0][0] = 0.0;		/* compute meanvalue */	mean_value = 0.0;	active_pels  = 0;	for (i = 0; i < bky; i++) {		for (j = 0; j < bkx; j++) {			active_pels+= mask[i][j];			mean_value += in[i][j] * mask[i][j];		}	}		if (active_pels)		mean_value = mean_value / (Float)active_pels;	mean_value = mean_value + 0.5;	mean_value = (int)mean_value;		for (i = 0; i < bky; i++) {		for (j = 0; j < bkx; j++) {			in[i][j] -= mean_value;		}	}	 	transform(out, lx, in, mask, bky, bkx);		/* copy meanvalue to DC-coefficient */	out[0][0] = mean_value * 8.0;	}// HHI Schueuer: inserted for fast sadct#ifdef _FAST_SADCT_Void CFwdSADCT::fast_deltaDCTransform(Float **out, Int *lx, Float **in, PixelC **mask, Int bky, Int bkx){	Int i, j, jmax, k;	Float mean_value;	Float *row, *row_coeff;	Int active_pels;	out[0][0] = 0.0;		/* compute meanvalue */	// mean_value = 0.0;	// active_pels  = 0;	fastshiftupTranspose(m_mat_tmp1, m_ly, in, mask, &mean_value, &active_pels, bky, bkx);	if (active_pels) {		mean_value /= (Float) active_pels;		if (mean_value > 0)			mean_value = (Int) (mean_value + 0.5);		else			mean_value = (Int) (mean_value - 0.5);	}	memset(lx, 0, sizeof(Int)*bky);		for (i=0; i<bkx && m_ly[i]; i++) {		jmax = m_ly[i];		row = m_mat_tmp1[i];		for (j = 0; j < jmax; j++)			row[j] -= mean_value;		switch (jmax) {		case 1:			c_buf[0] = row[0];			break;      		case 2:			dct_vec2 (row, c_buf);			break;		case 3:			dct_vec3 (row, c_buf);			break;		case 4:			dct_vec4 (row, c_buf);			break;      		case 5:			dct_vec5 (row, c_buf);			break;		case 6:			dct_vec6 (row, c_buf);			break;		case 7:			dct_vec7 (row, c_buf);			break;		case 8:			dct_vec8 (row, c_buf);			break;	}      	for (k=0; k<jmax; k++) {      tmp_out[k][lx[k]] = c_buf[k];      lx[k]++;    }  }		/* and finally the horizontal transformation */	for (i=0; i<bky && lx[i]; i++) {		jmax = lx[i];		row = out[i];		row_coeff = tmp_out[i];		switch (jmax) {		case 1:			*row = row_coeff[0];			break;      		case 2:			dct_vec2 (row_coeff, row);		 break;		case 3:			dct_vec3 (row_coeff, row);			break;		case 4:			dct_vec4 (row_coeff, row);			break;      		case 5:			dct_vec5 (row_coeff, row);			break;		case 6:			dct_vec6 (row_coeff, row);			break;		case 7:			dct_vec7 (row_coeff, row);			break;		case 8:			dct_vec8 (row_coeff, row);			break;		}	} 

⌨️ 快捷键说明

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