拉丁矩阵问题 利用回溯法的C++实现方案
Posted 枯萎的海风
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了拉丁矩阵问题 利用回溯法的C++实现方案相关的知识,希望对你有一定的参考价值。
这两天正好在赶算法设计的作业,这里把做的几个需要写代码的题放上来,方便以后查看。
1.题目要求
2.算法思想
这个题目基本思想是 利用回溯法,对于 m 行 n 列, 本质上就是一个二维数组, 我们可以将问题的解写成 x[1],x[2],x[3] … x[m*n], 那么对于每个点 x[i] 的取值实际上是 [1, n], 套用回溯法的算法框架,这里的 约束条件 ,就是同行,同列 没有相同的取值, 并且这里没有优化目标,只要类似 N后问题找出所有解就可以了。
另外,回溯时候的边界条件,需要特别注意一下,由于我们把二维数组当作一维数组进行实现, 下标从 0 开始, 理论上到 m*n-1就应该结束了,一开始没怎么注意,导致调试了好久 *23333333333*
3.算法实现源码:
3.1 LatiMatrix.h
// -------------------------【chp 5 HW 拉丁矩阵 宝石排列 】----------------------
// @ author : zhyh2010
// @ date : 20150524
// @ version : 1.0
// @ description : 有n种不同形状的宝石,每种都足够多,现要求将他们排列成
// m行 n 列 的矩阵 (m <= n) 使每行,每列 中的宝石形状不同
// 求, 给定 m,n 时候有多少种算法
// @ idea : 回溯法
// -----------------------------------【end tip】-------------------------------
#pragma once
class CLatiMatrix
public:
CLatiMatrix();
~CLatiMatrix();
int solve();
private:
void BackTrace(int id);
void output();
bool isOK(int row, int col);
void ReadFile();
void WriteFile();
private:
int m_m;
int m_n;
int ** m_matrix;
int m_solution_num;
;
3.2.LatiMatrix.cpp
#include "LatiMatrix.h"
#include <cstdio>
#include <cstdlib>
#include <fstream>
CLatiMatrix::CLatiMatrix()
m_m = 0;
m_n = 0;
m_matrix = NULL;
m_solution_num = 0;
CLatiMatrix::~CLatiMatrix()
for (int i = 0; i != m_n; i++)
if (m_matrix[i])
delete m_matrix[i];
if (m_matrix)
delete [] m_matrix;
void CLatiMatrix::BackTrace(int id)
// ===============【这里一开始写的时候没有加 = 号 导致出问题】=================
if (id >= m_m * m_n)
output();
return;
int row = id / m_n;
int col = id % m_n;
for (int k = 0; k != m_n; k++)
m_matrix[row][col] = k;
if (isOK(row, col))
id++;
BackTrace(id);
id--;
void CLatiMatrix::output()
m_solution_num++;
bool CLatiMatrix::isOK(int row, int col)
int k = m_matrix[row][col];
for (int i = 0; i != col; i++)
if (k == m_matrix[row][i])
return false;
for (int i = 0; i != row; i++)
if (k == m_matrix[i][col])
return false;
return true;
void CLatiMatrix::ReadFile()
std::ifstream infile("input.txt");
infile >> m_m >> m_n;
m_matrix = new int *[m_m];
for (int i = 0; i != m_n; i++)
m_matrix[i] = new int[m_n];
memset(m_matrix[i], 0, sizeof(m_matrix[i]));
void CLatiMatrix::WriteFile()
std::ofstream outfile("output.txt");
outfile << m_solution_num << std::endl;
int CLatiMatrix::solve()
ReadFile();
BackTrace(0);
WriteFile();
return m_solution_num;
3.3.Main.cpp
// -------------------------【chp 5 HW 拉丁矩阵 宝石排列】----------------------
// @ author : zhyh2010
// @ date : 20150524
// @ version : 1.0
// @ description : 有n种不同形状的宝石,每种都足够多,现要求将他们排列成
// m行 n 列 的矩阵 (m <= n) 使每行,每列 中的宝石形状不同
// 求, 给定 m,n 时候有多少种算法
// @ idea : 回溯法
// -----------------------------------【end tip】-------------------------------
#include "LatiMatrix.h"
#include <iostream>
void main()
CLatiMatrix instance;
int res = instance.solve();
std::cout << "res = " << res << std::endl;
以上是关于拉丁矩阵问题 利用回溯法的C++实现方案的主要内容,如果未能解决你的问题,请参考以下文章