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

📄 i6r.c

📁 calc大数库
💻 C
📖 第 1 页 / 共 3 页
字号:

MPMATR *TRANSPOSER(MPMATR *Mptr)
/* 
 * returns the transpose of *Mptr.
 */
{
	MPMATR *Nptr;
	unsigned int i, j;

	Nptr = BUILDMATR(Mptr->C, Mptr->R);
	for (j = 0; j <= Nptr->R - 1; j++)
		for (i = 0; i <= Nptr->C - 1; i++)
			elt(Nptr, j, i) = COPYR(elt(Mptr, i, j));
	return (Nptr);
}

MPMATR *MULTMATR(MPMATR *Mptr, MPMATR *Nptr)
/*
 * Here Mptr->C = Nptr->R. 
 * returns (*Mptr) * (*Nptr).
 */
{
	MPR *X, *Y, *Temp;
	unsigned int i, j, k;
	MPMATR *Lptr;

	Lptr = BUILDMATR(Mptr->R, Nptr->C);
	for (i = 0; i <= Mptr->R - 1; i++)
	{
		for (j = 0; j <= Nptr->C - 1; j++)
		{
			X = ZEROR();
			for (k = 0; k <= Mptr->C - 1; k++)
			{
				Y = MULTR(elt(Mptr, i, k), elt(Nptr, k, j));
				Temp = X;
				X = ADDR(X, Y);
				FREEMPR(Temp);
				FREEMPR(Y);
			}
			elt(Lptr, i, j) = X;
		}
	}
	return (Lptr);
}

void SHORTEST(MPMATI *AA, MPI *I[], USI filename, USI number)
/*
 * Input: An m x m matrix of integers AA = Q arising from the EXTGCD
 * LLLGCD or LLLGCD0. The last row of AA is assumed to be a multiplier
 * of shortest length.
 * Output:  All multipliers of shortest length.
 * filename:1->egcdmult.out,2->lllgcdmult.out,3->lllgcd0mult.out.
 * 4->gcd3.out (used in GCD3()).
 * If number = 0, no printing.
 * If number > 0 prints out multipliers on screen and in .out file.
 * Only used in nfunc.c.
 */
{
	unsigned int i, j, k, m, n, *l, *u, *t, *x, w, count = 0;
	MPR **X, **Y, **L, **T, **U, **V, *Temp0, *Temp1, *Temp2, *Temp3; 
        MPR *C, *Z, *ONE, *SUM, **N, *temp, *tempR, **XX;
	MPI *lengthi;
	char buff[25]; 
	FILE *outfile;
	MPMATR *A, *B, *BB, *Q, *QQ, *MATR, *VECTOR;
	MPMATI *MATI;
	int e;
	
/* First get the vector [V[0],...,V[n-2], where V[i]=<A[n-1][*],A[i][*]>.*/
	m = AA->C;
	n = (AA->R) - 1;
	A = BUILDMATR(n + 1, m);
	for (i = 0; i < n + 1; i++)
		for (j = 0; j < m; j++)
		{
			elt(A, i, j) = BUILDMPR();
			elt(A, i, j)->N = COPYI(AA->V[i][j]);
			elt(A, i, j)->D = ONEI();
		}

	V = (MPR **)mmalloc(n * sizeof(MPR *));
	for (i = 0; i < n; i++)
	{
		V[i] = ZEROR();
		for (j = 0; j < m; j++)
		{
			Temp1 = V[i];
			Temp2 = MULTR(elt(A, n, j), elt(A, i, j));
			V[i] = ADDR(V[i], Temp2);
			FREEMPR(Temp1);
			FREEMPR(Temp2);
		}
	}
	B = TRANSPOSER(A);
	BB = MULTMATR(A, B);
	FREEMATR(B);
	Q = CHOLESKYR(BB);
	FREEMATR(BB);
	QQ = COPYMATR(Q);
	for (i = 0; i < n; i++)
	{
		FREEMPR(elt(QQ, i, i));
		elt(QQ, i, i) = ONER();
	}
/* Calculate (U^{-1})^tV = Y */
	MATR = QQ;
	QQ = TRANSPOSER(QQ);
	FREEMATR(MATR);
	Y = (MPR **)mmalloc(n * sizeof(MPR *));
	Y[0] = COPYR(V[0]);
	for (w = 1; w < n; w++)
	{
		SUM = ZEROR();
		for ( k = 0; k < w; k++)
		{
			Temp1 = SUM;
			Temp2 = MULTR(elt(QQ, w, k), Y[k]);
			SUM = ADDR(SUM, Temp2);
			FREEMPR(Temp1);
			FREEMPR(Temp2);
		}
		Y[w] = SUBR(V[w], SUM);
		FREEMPR(SUM);
	}
	FREEMATR(QQ);
	N = (MPR **)mmalloc(n * sizeof(MPR *));
	for (j = 0; j < n; j++)
		N[j] = RATIOR(Y[j], elt(Q, j, j));
	if (filename == 1)
		strcpy(buff, "egcdmult.out");
	else if (filename == 2)
		strcpy(buff, "lllgcdmult.out");
	else if (filename == 3)
		strcpy(buff, "lllgcd0mult.out");
	else if (filename == 4)
		strcpy(buff, "gcd3.out");
	else if (filename == 5)
		strcpy(buff, "axb.out");
	outfile = fopen(buff, "a");
	ONE = ONER();
	X = (MPR **)mmalloc(n * sizeof(MPR *));
	L = (MPR **)mmalloc(n * sizeof(MPR *));
	T = (MPR **)mmalloc(n * sizeof(MPR *));
	U = (MPR **)mmalloc(n * sizeof(MPR *));
	l = (USI *)mmalloc(n * sizeof(USI));
	t = (USI *)mmalloc(n * sizeof(USI));
	u = (USI *)mmalloc(n * sizeof(USI));
	x = (USI *)mmalloc(n * sizeof(USI));
	for (j = 0; j < n; j++)
	{
		l[j] = 0;
		t[j] = 0;
		u[j] = 0;
		x[j] = 0;
	}
	C = ZEROR();
	for (i = 0; i < n; i++)
	{
		Temp1 = C;
		Temp2 = MULTR(Y[i], Y[i]);
		Temp3 = RATIOR(Temp2, elt(Q, i, i));
		C = ADDR(C, Temp3);
		FREEMPR(Temp1);
		FREEMPR(Temp2);
		FREEMPR(Temp3);
	}
	i = n - 1;
	T[i] = COPYR(C); t[i] = 1;
	FREEMPR(C);
	U[i] = ZEROR(); u[i] = 1;
bounds:
	Z = RATIOR(T[i], elt(Q, i, i));
	Temp2 = SUBR(N[i], U[i]);
	if (l[i])
		FREEMPR(L[i]); 
	else
		l[i] = 1;
	L[i] = INTROOT(Z, Temp2);
	FREEMPR(Temp2);
	Temp0 = SUBR(U[i], N[i]);
	Temp2 = INTROOT(Z, Temp0); 
	FREEMPR(Temp0);
	Temp3 = MINUSR(Temp2);
	if (x[i])
		FREEMPR(X[i]);
	else
		x[i] = 1;
	X[i] = SUBR(Temp3, ONE);
	FREEMPR(Z);
	FREEMPR(Temp2);
	FREEMPR(Temp3);
loop:
	Temp1 = X[i];
	X[i] = ADDR(X[i], ONE);
	FREEMPR(Temp1);
	if (COMPAREI(X[i]->N, L[i]->N) == 1)
	{
		i++;
		if (i == n)
			goto exiting;
		else
			goto loop;
	}
	else
	{
		if (i)
		{
			Temp1 = ADDR(X[i], U[i]);
			Temp0 = SUBR(Temp1, N[i]);
			FREEMPR(Temp1);
			Temp2 = MULTR(Temp0, Temp0);
			FREEMPR(Temp0);
			Temp1 = MULTR(elt(Q, i, i), Temp2);
			FREEMPR(Temp2);
			if (t[i - 1])
				FREEMPR(T[i - 1]);
			else
				t[i - 1] = 1;
			T[i - 1] = SUBR(T[i], Temp1);
			FREEMPR(Temp1);
			i--;
			SUM = ZEROR();
			for (j = i + 1; j < n; j++)
			{
				Temp1 = SUM;
				Temp2 = MULTR(elt(Q, i, j), X[j]);
				SUM = ADDR(SUM, Temp2);
				FREEMPR(Temp1);
				FREEMPR(Temp2);
			}
			if (u[i])
				FREEMPR(U[i]);
			else
				u[i] = 1;
			U[i] = COPYR(SUM);
			FREEMPR(SUM);
			goto bounds;
		}
		else
			goto found;
	}
	
	found:
		VECTOR = BUILDMATR(1, AA->R);
		XX = (MPR **)mmalloc((USL)(n * sizeof(MPR *)));
		for (j = 0; j < n; j++)
		{
			tempR = BUILDMPR();
			tempR->N = COPYI(I[j]);
			tempR->D = ONEI();
			XX[j] = ADDR(X[j], tempR);
			FREEMPR(tempR);
		}
if (number)
{
		printf("\tMULTIPLIER[%u] = ", count + 1);
		fprintf(outfile, "\tMULTIPLIER[%u]:", count + 1);
		printf("b[%u]", n + 1);
		fprintf(outfile, "b[%u]", n + 1);
		for (j = 0; j < n; j++)
		{
			e = (XX[j]->N)->S;
			if (e == -1)
			{
				printf("+");
				fprintf(outfile, "+");
				temp = MINUSR(XX[j]);
				if (!EQONER(temp))
				{
					PRINTR(temp);
					FPRINTR(outfile, temp);
				}
				printf("b[%u]", j + 1);
				fprintf(outfile, "b[%u]", j + 1);
				FREEMPR(temp);
			}
			if (e == 1)
			{
				printf("-");
				fprintf(outfile, "-");
				if (!EQONER(XX[j]))
				{
					PRINTR(XX[j]);
					FPRINTR(outfile, XX[j]);
				}
				printf("b[%u]", j + 1);
				fprintf(outfile, "b[%u]", j + 1);
			}
		}
}
		for (j = 0; j < n; j++)
		{
			elt(VECTOR, 0, j) = MINUSR(X[j]);
			FREEMPR(XX[j]);
		}
		ffree((char *)XX, n * sizeof(MPR *));
		elt(VECTOR, 0, n) = ONER();
		MATR = MULTMATR(VECTOR, A);
		FREEMATR(VECTOR);
if (number)
{
		printf("=");
		fprintf(outfile, "=");
}
		MATI = BUILDMATI(1, m);
		for (j = 0; j < m; j++)
			MATI->V[0][j] = COPYI((elt(MATR, 0, j))->N);
if (number)
{
		for (j = 0; j < m; j++)
		{
			PRINTI(MATI->V[0][j]);
			FPRINTI(outfile, MATI->V[0][j]);
			printf(" ");
			fprintf(outfile, " ");
		}
		fprintf(outfile, ": ");
		printf(": ");
}
		lengthi = LENGTHSQRI(MATI, 0);
if (number)
{

		FPRINTI(outfile, lengthi);
		fprintf(outfile, "\n");
		PRINTI(lengthi);
		printf("\n");
}
		FREEMPI(lengthi);
		FREEMATR(MATR);
		FREEMATI(MATI);
		count++;
		goto loop;
exiting:
		FREEMPR(ONE);
		for (j = 0; j < n; j++)
		{
			FREEMPR(N[j]);
			FREEMPR(X[j]);
			FREEMPR(L[j]);
			FREEMPR(T[j]);
			FREEMPR(U[j]);
			FREEMPR(Y[j]);
			FREEMPR(V[j]);
		}
		ffree((char *)N, n * sizeof(MPR *));
		ffree((char *)V, n * sizeof(MPR *));
		ffree((char *)Y, n * sizeof(MPR *));
		ffree((char *)X, n * sizeof(MPR *));
		ffree((char *)L, n * sizeof(MPR *));
		ffree((char *)T, n * sizeof(MPR *));
		ffree((char *)U, n * sizeof(MPR *));
		ffree((char *)l, n * sizeof(USI));
		ffree((char *)t, n * sizeof(USI));
		ffree((char *)u, n * sizeof(USI));
		ffree((char *)x, n * sizeof(USI));
		FREEMATR(Q);
		FREEMATR(A);
if (number)
{
		if (count > 1)
		{
			fprintf(outfile, "\tThere are exactly %u shortest multiplier vectors\n", count);
			printf("\tThere are exactly %u shortest multiplier vectors\n", count);
		}
		if (count == 1)
		{
			printf("\tThere is exactly one shortest multiplier vector\n");
			fprintf(outfile, "\tThere is exactly one shortest multiplier vector\n");
		}
}
		fclose(outfile);
		return;
}

void SHORTESTTT(MPMATI *AA, MPI *BOUND)
/*
 * This is used in INHOMFP().
 * Input: An m x M matrix of integers AA whose first m - 1 rows Q[0],... * ,Q[m-2] are LI and span a lattice L.
 * Output: If P is the last row, finds all x[0],...,x[m-2]
 * satisfying ||P -x[0]Q[0]-...-x[m-2]Q[m-2]||^2<=BOUND.
 */
{
	unsigned int i, j, k, m, n, *l, *u, *t, *x, w, count = 0;
	unsigned int M, FLAG;
	MPR **X, **Y, **L, **T, **U, **V, *Temp0, *Temp1, *Temp2, *Temp3; 
        MPR *C, *Z, *ONE, *SUM, **N, *temp;
	MPI *lengthi, *lengthj, *TempI1, *TempI2;
	MPMATR *A, *B, *BB, *Q, *QQ, *MATR, *VECTOR;
	MPMATI *MATI;
	int e;
	char buff[25]; 
	FILE *outfile;
	
	strcpy(buff, "inhomfp.out");
	outfile = fopen(buff, "w");
/* Compute ||AA[m - 1][*]||^2. */
	m = AA->R;
	M = AA->C;
	n = m - 1;
	lengthj = ZEROI();
	for (j = 0; j < M; j++)
	{
		TempI1 = lengthj;
		TempI2 = MULTI(AA->V[n][j], AA->V[n][j]);
		lengthj = ADDI(lengthj, TempI2);
		FREEMPI(TempI1);
		FREEMPI(TempI2);
	}
/* First get the vector [V[0],...,V[n-2], where V[i]=<A[n-1][*],A[i][*]>.*/
	A = BUILDMATR(m, M);
	for (i = 0; i < m; i++)
		for (j = 0; j < M; j++)
		{
			elt(A, i, j) = BUILDMPR();
			elt(A, i, j)->N = COPYI(AA->V[i][j]);
			elt(A, i, j)->D = ONEI();
		}

	V = (MPR **)mmalloc(n * sizeof(MPR *));
	for (i = 0; i < n; i++)
	{
		V[i] = ZEROR();
		for (j = 0; j < M; j++)
		{
			Temp1 = V[i];
			Temp2 = MULTR(elt(A, n, j), elt(A, i, j));
			V[i] = ADDR(V[i], Temp2);
			FREEMPR(Temp1);
			FREEMPR(Temp2);
		}
	}
	B = TRANSPOSER(A);
	BB = MULTMATR(A, B);
	FREEMATR(B);
	Q = CHOLESKYR(BB);
	FREEMATR(BB);
	QQ = COPYMATR(Q);
	for (i = 0; i < n; i++)
	{
		FREEMPR(elt(QQ, i, i));
		elt(QQ, i, i) = ONER();
	}
/* Calculate (U^{-1})^tV = Y */
	MATR = QQ;
	QQ = TRANSPOSER(QQ);
	FREEMATR(MATR);
	Y = (MPR **)mmalloc(n * sizeof(MPR *));
	Y[0] = COPYR(V[0]);
	for (w = 1; w < n; w++)
	{
		SUM = ZEROR();
		for ( k = 0; k < w; k++)
		{
			Temp1 = SUM;
			Temp2 = MULTR(elt(QQ, w, k), Y[k]);
			SUM = ADDR(SUM, Temp2);
			FREEMPR(Temp1);
			FREEMPR(Temp2);
		}
		Y[w] = SUBR(V[w], SUM);
		FREEMPR(SUM);
	}
	FREEMATR(QQ);
	N = (MPR **)mmalloc(n * sizeof(MPR *));
	for (j = 0; j < n; j++)
		N[j] = RATIOR(Y[j], elt(Q, j, j));
	ONE = ONER();
	X = (MPR **)mmalloc(n * sizeof(MPR *));
	L = (MPR **)mmalloc(n * sizeof(MPR *));
	T = (MPR **)mmalloc(n * sizeof(MPR *));
	U = (MPR **)mmalloc(n * sizeof(MPR *));
	l = (USI *)mmalloc(n * sizeof(USI));
	t = (USI *)mmalloc(n * sizeof(USI));
	u = (USI *)mmalloc(n * sizeof(USI));
	x = (USI *)mmalloc(n * sizeof(USI));
	for (j = 0; j < n; j++)
	{
		l[j] = 0;
		t[j] = 0;
		u[j] = 0;
		x[j] = 0;
	}
	C = ZEROR();
	for (i = 0; i < n; i++)
	{
		Temp1 = C;
		Temp2 = MULTR(Y[i], Y[i]);
		Temp3 = RATIOR(Temp2, elt(Q, i, i));
		C = ADDR(C, Temp3);
		FREEMPR(Temp1);
		FREEMPR(Temp2);
		FREEMPR(Temp3);
	}
	
	Temp0 = BUILDMPR();
	Temp0->N = SUBI(BOUND, lengthj);
	Temp0->D = ONEI();
	Temp1 = C;
	C = ADDR(C, Temp0);
	FREEMPR(Temp0);
	FREEMPR(Temp1);
		
	i = n - 1;
	T[i] = COPYR(C); t[i] = 1;
	FREEMPR(C);
	U[i] = ZEROR(); u[i] = 1;
bounds:
	Z = RATIOR(T[i], elt(Q, i, i));
	Temp2 = SUBR(N[i], U[i]);
	if (l[i])
		FREEMPR(L[i]); 
	else
		l[i] = 1;
	L[i] = INTROOT(Z, Temp2);
	/*printf("at L[%u]\n", i);*/
	FREEMPR(Temp2);
	Temp0 = SUBR(U[i], N[i]);
	Temp2 = INTROOT(Z, Temp0); 
	FREEMPR(Temp0);
	Temp3 = MINUSR(Temp2);
	if (x[i])
		FREEMPR(X[i]);
	else
		x[i] = 1;
	X[i] = SUBR(Temp3, ONE);
	FREEMPR(Z);
	FREEMPR(Temp2);
	FREEMPR(Temp3);
loop:
	Temp1 = X[i];
	X[i] = ADDR(X[i], ONE);
	FREEMPR(Temp1);
	if (COMPAREI(X[i]->N, L[i]->N) == 1)
	{
		i++;
		if (i == n)
			goto exiting;
		else
			goto loop;
	}
	else
	{
		if (i)
		{
			Temp1 = ADDR(X[i], U[i]);
			Temp0 = SUBR(Temp1, N[i]);
			FREEMPR(Temp1);
			Temp2 = MULTR(Temp0, Temp0);
			FREEMPR(Temp0);
			Temp1 = MULTR(elt(Q, i, i), Temp2);
			FREEMPR(Temp2);
			if (t[i - 1])
				FREEMPR(T[i - 1]);
			else
				t[i - 1] = 1;
			T[i - 1] = SUBR(T[i], Temp1);
			FREEMPR(Temp1);
			i--;
			SUM = ZEROR();
			for (j = i + 1; j < n; j++)
			{
				Temp1 = SUM;
				Temp2 = MULTR(elt(Q, i, j), X[j]);
				SUM = ADDR(SUM, Temp2);
				FREEMPR(Temp1);
				FREEMPR(Temp2);
			}
			if (u[i])
				FREEMPR(U[i]);
			else
				u[i] = 1;
			U[i] = COPYR(SUM);
			FREEMPR(SUM);
			goto bounds;
		}
		else
			goto found;
	}
	
	found:
		VECTOR = BUILDMATR(1, AA->R);
		for (j = 0; j < n; j++)
		{
			/*
			printf("X[%u][%u] = ", count, j);
			PRINTR(X[j]);
			printf("\n");
			fprintf(outfile, "X[%u][%u] = ", count, j);
			FPRINTR(outfile, X[j]);
			fprintf(outfile,"\n");
*/
			elt(VECTOR, 0, j) = COPYR(X[j]);
		}
		elt(VECTOR, 0, n) = ZEROR();
		MATR = MULTMATR(VECTOR, A);
		FREEMATR(VECTOR);
		printf("LV[%u] = ", count + 1);
		fprintf(outfile, "LV[%u] = ", count + 1);

⌨️ 快捷键说明

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