uva_10604 - Chemical Reaction( Hash+状态压缩 )
来源:互联网 发布:雨果博斯 知乎 编辑:程序博客网 时间:2024/06/05 15:23
这个题一开始想用六维数组直接跑的,但是考虑到药物或者序列更多的话就不实际了,这里我是用了hash对状态压缩然后DPhash: elfhash状态: 就是序列, 对应不同的结果保存最小解然后递归记忆求解#include <cstdio>#include <cstring>#include <algorithm>using namespace std;#define MAXV 10#define MAXC 11#define MAXN 1000001#define INF 0x7ffffffftypedef struct NODE_ { int heat; char mix_rst;}NODE;int hash[MAXN], ans;NODE tab[MAXV][MAXV];char save[MAXN][MAXC], t[MAXC];inline int elf_hash(char *str){ unsigned long h( 0x0L ), x( 0x0L ); strcpy(t, str); char *ptr = t; while( *ptr ) { h = (h<<4)+(*ptr ++); if( (x = h&0xF0000000L) ) { h ^= (x>>24); h &= ~x; } } int idx( h%MAXN ); while( (INF != hash[idx]) && strcmp(str, save[idx]) ) { idx = (idx+1)%MAXN; } strcpy(save[idx], str); return idx;}inline int mix_chemical(const char *str, const int &idx1, const int &idx2, char *des){ int x, y, s, f, idx(0), flag(0); x = str[idx1]-'0'; y = str[idx2]-'0'; s = min(idx1, idx2); f = max(idx1, idx2); des[idx ++] = tab[x][y].mix_rst; for(int i = 0; i < strlen(str); i ++) { if( i != idx1 && i != idx2 ) { des[idx ++] = str[i]; } } des[idx] = '\0'; return tab[x][y].heat;}int dfs(char *str){ if( 2 > strlen(str) ) { return 0; } char tmp[MAXC]; int idx( elf_hash(str) ), rst(INF), x, y; if( INF != hash[idx] ) { return hash[idx]; } for(int i = 0; i < strlen(str); i ++) { for(int j = i+1; j < strlen(str); j ++) { rst = min(rst, mix_chemical(str, i, j, tmp)+dfs(tmp)); rst = min(rst, mix_chemical(str, j, i, tmp)+dfs(tmp)); } } return hash[idx] = rst;}int main(int argc, char const *argv[]){#ifndef ONLINE_JUDGE freopen("test.in", "r", stdin);#endif int cas, n, m, v; char str[MAXC], ch[3]; scanf("%d", &cas); for( ; cas; cas --) { scanf("%d", &n); for(int i = 1; i <= n; i ++) { for(int j = 1; j <= n; j ++) { scanf("%d %d", &v, &tab[i][j].heat); tab[i][j].mix_rst = v+'0'; } } scanf("%d", &m); for(int i = 0; i < m; i ++) { scanf("%d", &v); str[i] = v+'0'; } str[m] = '\0'; scanf("%s", ch); ans = INF; memset(save, '\0', sizeof(save)); for(int i = 0; i < MAXN; i ++) { hash[i] = INF; } printf("%d\n", dfs(str)); } return 0;}