任意交换两个数最优解的和都会增大这个没啥好证明的~但现在纠结的是它的逆命题~任意交换两个数其和都会增大的必然是最优解~这个命题是否成立~~~
[code]/*~个性签名:bug是什么意思?bug是看上去没有可能的东西实际上是有可能做到的 就是这样~2018-08-08更~*/[/code]
#include <stdio.h> #include <assert.h> #define MAX_ARY_LEN (100) unsigned int ary_len; unsigned int two_ary[MAX_ARY_LEN][MAX_ARY_LEN]; struct{ unsigned int row; ///< 行 unsigned int col; ///< 列 unsigned int val; ///< 值 }list_st[MAX_ARY_LEN * MAX_ARY_LEN]; unsigned int row_ary[MAX_ARY_LEN]; unsigned int col_ary[MAX_ARY_LEN]; /** *\brief 捕获输入 */ void get_input(void) { unsigned int i = 0, j = 0; scanf("%u", &ary_len); assert(ary_len > 1 && ary_len <= 100); for (i = 0; i < ary_len; ++i){ for (j = 0; j < ary_len; ++j){ scanf("%u", &two_ary[i][j]); list_st[i * ary_len + j].row = i; list_st[i * ary_len + j].col = j; list_st[i * ary_len + j].val = two_ary[i][j]; } row_ary[i] = ary_len; col_ary[i] = ary_len; } } /** *\brief 对list_st 排序 */ void sort_list(void) { unsigned int total = ary_len * ary_len; unsigned int i = 0, j = 0; /* 选择 */ for (i = 0; i < total; ++i){ for (j = i + 1; j < total; ++j){ if (list_st[i].val < list_st[j].val){ list_st[i].row += list_st[j].row; list_st[i].col += list_st[j].col; list_st[i].val += list_st[j].val; list_st[j].row = list_st[i].row - list_st[j].row; list_st[j].col = list_st[i].col - list_st[j].col; list_st[j].val = list_st[i].val - list_st[j].val; list_st[i].row -= list_st[j].row; list_st[i].col -= list_st[j].col; list_st[i].val -= list_st[j].val; } } } } /** *\brief 选择 */ void select_num(void) { unsigned int total = ary_len * ary_len; unsigned int i = 0, j = 0, sum = 0; /* 选择 */ for (i = 0; i < total; ++i){ unsigned int row = list_st[i].row; unsigned int col = list_st[i].col; if (row_ary[row] > 1 && col_ary[col] > 1){ --row_ary[row]; --col_ary[col]; }else if(row_ary[row] == 1){/* 行唯一 */ sum += list_st[i].val; printf("(%u, %u) ", row, col); --row_ary[row]; }else{/* 列唯一 */ sum += list_st[i].val; printf("(%u, %u) ", row, col); --col_ary[col]; } } printf("\n sum[%u]\n", sum); } int main(void) { get_input(); sort_list(); select_num(); return 0; }
/** *\brief 选择 */ void select_num(void) { unsigned int total = ary_len * ary_len; unsigned int i = 0, j = 0, sum = 0; /* 选择 */ for (i = 0; i < total; ++i){ unsigned int row = list_st[i].row; unsigned int col = list_st[i].col; if (row_ary[row] > 1 && col_ary[col] > 1){ --row_ary[row]; --col_ary[col]; }else if(row_ary[row] == 1){/* 行唯一 */ sum += list_st[i].val; printf("(%u, %u) ", row, col); --row_ary[row]; /* 剩余所有行 都要改变 */ for (j = 0; j < ary_len; ++j){ if (row_ary[j] > 0){ --row_ary[j]; } } }else if(col_ary[col] == 1){/* 列唯一 */ sum += list_st[i].val; printf("(%u, %u) ", row, col); --col_ary[col]; /* 剩余所有列 都要改变*/ for (j = 0; j < ary_len; ++j){ if (col_ary[j] > 0){ --col_ary[j]; } } } } printf("\n sum[%u]\n", sum); }
#include <stdio.h> #include <stdlib.h> #include <time.h> #include <math.h> int compares(void *a, void *b); int makeresult( struct s *des, struct s *src); void printresult(struct s *input); struct s { int value; int row; int col; }; int main(void) { clock_t t = clock(); int i = 0, j = 0; struct s result[4]; struct s tmp[16]; int matrix[4][4] = { {1, 3, 5, 7, }, {1, 1, 3, 5, }, {3, 1, 1, 3, }, {5, 3, 1, 1, }, }; for( i = 0; i < 4; i += 1 ) for( j = 0; j < 4; j += 1 ) { tmp[i * 4 + j].value = matrix[i][j]; tmp[i * 4 + j].row = i; tmp[i * 4 + j].col = j; } for( i = 0; i < 16; i += 1 ) printf("%d%c", tmp[i].value, 0 == (i + 1 & 3) ? '\n' : ' '); qsort(tmp, 16, sizeof tmp[0], compares); if( 4 == makeresult(result, tmp) ) printresult(result); else printf("fatal error!\n"); printf("\nthis program cost %f second!\n", (double)(clock() - t) / CLOCKS_PER_SEC); getchar(); return 0; } int compares(void *a, void *b) { if( ((struct s*)a)->value == ((struct s*)b)->value ) return ((struct s*)a)->row + ((struct s*)a)->col == ((struct s*)b)->row + ((struct s*)b)->col ? ((struct s*)a)->row > ((struct s*)b)->row ? 1 : -1 : ((struct s*)a)->row + ((struct s*)a)->col > ((struct s*)b)->row + ((struct s*)b)->col ? 1 : -1; else return ((struct s*)a)->value > ((struct s*)b)->value ? 1 : -1; } int makeresult( struct s *des, struct s *src) { int i = 0, j = 0, count = 0, row = 0, col = 0; for( i = 0; i < 16; i += 1 ) if( -1 != src[i].value ) { memcpy(des++, src + i, sizeof(struct s)); row = src[i].row; col = src[i].col; printf("%d, %d\n", src[i].row, src[i].col); for( j = 0; j < 16; j += 1 ) { if( src[j].row == row ) src[j].value = -1; if( src[j].col == col ) src[j].value = -1; } count += 1; } else continue; return count; } void printresult(struct s *input) { int i = 0, sum = 0; for( i = 0; i < 4; i += 1 ) { printf("(%d, %d)\n", input[i].row, input[i].col); sum += input[i].value; } printf("sum = %d\n", sum); return; }
#include <stdio.h> #include <limits.h> #include <stdbool.h> #define N 4 bool visit[N]; int map[N][N], ans[N] = {0}, res; void print(int len) { for (int i = 0; i < len; ++i) printf("{%d, %d}, ", i + 1, ans[i] + 1); printf("%d\n", res); } void dfs(int len, int pos, int ss) { if (len == pos) { if (res < ss) return; res = ss, print(len); return; } if (ss > res) return; // 剪枝 for (int i = 0; i < len; ++i) { if (visit[i]) continue; ans[pos] = i, visit[i] = true; dfs(len, pos + 1, ss + map[pos][i]); visit[i] = false; } } int main(int argc, char *argv[]) { int t; while (1 == scanf("%d", &t) && t) { res = INT_MAX; for (int i = 0; i < t * t; ++i) scanf("%d", &map[i % t][i / t]); dfs(t, 0, 0); } return 0; }
[此贴子已经被作者于2017-4-18 16:16编辑过]