求hack数据,#31错了
查看原帖
求hack数据,#31错了
247992
_Cloud_楼主2020/10/30 17:27

思路,求2最少,5最少的,取Min

#include <cstdio>
#include <algorithm>
using namespace std;

const int N = 1005;

void read(int &x) {
	char c = getchar();
	while (c < '0' || c >'9') c = getchar();
	for (x = 0; c >= '0' && c <= '9'; c = getchar())
		x = x * 10 + c - '0';
}

bool okf = false, okg = false;

int f[N][N], g[N][N];//f->2, g->5

struct Front {
	int x, y;
} ff[N][N], gf[N][N];

struct Num {
	int num, two, five;
} map[N][N];

int findf(int x, int y) {
	if (x == 0 || y == 0 || x < 0 || y < 0)
		return 0;
	if (map[x][y].num == 0)
		okf = true;
	return map[x][y].five + findf(ff[x][y].x, ff[x][y].y);//找f数组5的个数 
}

int findg(int x, int y) {
	if (x == 0 || y == 0 || x < 0 || y < 0)
		return 0;
	if (map[x][y].num == 0)
		okg = true;
	return map[x][y].two + findg(gf[x][y].x, gf[x][y].y);//找g数组2的个数 
}

void outf(int x, int y) {
	if (x == 1 && y == 1)
		return;
	outf(ff[x][y].x, ff[x][y].y);
	if (ff[x][y].x == x - 1)
		printf("D");
	else
		printf("R");
}

void outg(int x, int y) {
	if (x == 1 && y == 1)
		return;
	outg(gf[x][y].x, gf[x][y].y);
	if (gf[x][y].x == x - 1)
		printf("D");
	else
		printf("R");
}

int main() {
	int n; read(n);
	for (int i = 1; i <= n; i++)
		for (int j = 1; j <= n; j++) {
			read(map[i][j].num);
			int x = map[i][j].num;
			map[i][j].two = map[i][j].five = 0;
			while (x % 2 == 0 && x) map[i][j].two++, x /= 2;
			x = map[i][j].num;
			while (x % 5 == 0 && x) map[i][j].five++, x /= 5;
		}
	
	for (int i = 1; i <= n; i++)
		map[i][n + 1].five = map[i][n + 1].two = map[0][i].two = map[0][i].five = 0x3f;
	
	for (int i = 1; i <= n; i++) {//求f数组最优(2最少 
		for (int j = 1; j <= n; j++) {
			if (i - 1 >= 1 && j - 1 >= 1) {
				if (f[i - 1][j] < f[i][j - 1]) {
				f[i][j] = f[i - 1][j];
				ff[i][j].x = i - 1, ff[i][j].y = j;
				} else if (f[i - 1][j] >= f[i][j - 1]){
				f[i][j] = f[i][j - 1];
				ff[i][j].x = i; ff[i][j].y = j - 1;
				}
			} else if (i - 1 >= 1) {
				f[i][j] = f[i - 1][j];
				ff[i][j].x = i - 1, ff[i][j].y = j;
			} else if (j - 1 >= 1) {
				f[i][j] = f[i][j - 1];
				ff[i][j].x = i; ff[i][j].y = j - 1;
			}
			f[i][j] += map[i][j].two;
		} 
	}
	
	for (int i = 1; i <= n; i++) {//求g数组最优,5最少 
		for (int j = 1; j <= n; j++) {
			if (i - 1 >= 1 && j - 1 >= 1) {
				if (g[i - 1][j] < g[i][j - 1]) {
				g[i][j] = g[i - 1][j];
				gf[i][j].x = i - 1, gf[i][j].y = j;
				} else if (g[i - 1][j] >= g[i][j - 1]){
				g[i][j] = g[i][j - 1];
				gf[i][j].x = i; gf[i][j].y = j - 1;
				}
			} else if (i - 1 >= 1) {
				g[i][j] = g[i - 1][j];
				gf[i][j].x = i - 1, gf[i][j].y = j;
			} else if (j - 1 >= 1) {
				g[i][j] = g[i][j - 1];
				gf[i][j].x = i; gf[i][j].y = j - 1;
			}
			g[i][j] += map[i][j].five;
		} 
	}
	
	int five_f = findf(n, n);
	int two_g = findg(n, n);
	int ansf = min(five_f, f[n][n]), ansg = min(two_g, g[n][n]);//答案 
	if (okf == true) ansf = 1;
	if (okg == true) ansg = 1;//如果路径有0,就置为1 
	
	if (ansf < ansg) printf("%d\n", ansf), outf(n, n);
	else printf("%d\n", ansg), outg(n, n);
	return 0;
}
2020/10/30 17:27
加载中...