【推荐】极简数独1.0源码
前一段时间迷上数独,于是自己做了一个,仿MetroUI,看着蛮简单。如下:
支持自定义背景,快捷键等!
由于自知算法不是很好,所以在做这个的时候,使用了一些小技术!
大概说一下,具体的结构!
有四个小项目,从上到下,分别是:
Sudoku.CodeMonk(我自己实现的一个数独)
Sudoku.Common(数独接口和其他的公用类)
Sudoku.Test(测试项目)
Sudoku.WinForm(WinForm版的数独)
当然最关键的肯定是那个ISudoku接口,它定义了一系列的数独操作,比如生成数独,打开和保存数独,撤销重复等!具体如下:
using System;
using System.Collections.Generic;
namespace Sudoku.Common
{
public delegate void FinishHandler();
/// <summary>
/// 数独接口
/// </summary>
public interface ISudoku:IDisposable
{
event FinishHandler OnInitializeFinish;
event FinishHandler OnLoadFinish;
/// <summary>
/// 设置点
/// </summary>
/// <param name="x">x坐标</param>
/// <param name="y">y坐标</param>
/// <returns>点</returns>
byte this[byte x, byte y] { get; set; }
/// <summary>
/// 载入数独
/// </summary>
/// <param name="path">路径</param>
void Load(string path);
/// <summary>
/// 保存数独
/// </summary>
/// <param name="path">路径</param>
void Save(string path);
/// <summary>
/// 撤销
/// </summary>
void Undo();
/// <summary>
/// 重复
/// </summary>
void Redo();
/// <summary>
/// 重置
/// </summary>
void Reset();
/// <summary>
/// 初始化数独
/// </summary>
void Initialize();
/// <summary>
/// 获取数独数据
/// </summary>
/// <returns></returns>
byte[,] Current { get; }
/// <summary>
/// 原数组
/// </summary>
byte[,] Original { get; }
/// <summary>
/// 等级
/// </summary>
byte Level { get; set; }
/// <summary>
/// 是否完成
/// </summary>
bool IsFinish { get; }
/// <summary>
/// 设置或获取数独的解决方法
/// </summary>
ISudokuSolution Solution { get; set; }
/// <summary>
/// 使用内置的解决方法解决当前数独
/// </summary>
void Solve();
/// <summary>
/// 检测该位置的点是否能放置
/// </summary>
/// <param name="row">行坐标</param>
/// <param name="col">列坐标</param>
/// <param name="value">值</param>
/// <returns>如果能放置则返回true</returns>
bool CanSet(byte row, byte col, byte value);
/// <summary>
/// 获取该位置放置的值集合
/// </summary>
/// <param name="row">行坐标</param>
/// <param name="col">列坐标</param>
/// <returns>放置值的集合</returns>
List<byte> CanSetValues(byte row, byte col);
}
}
里面的ISudokuSolution定义了一些解数独的方法:
using System.Collections.Generic;
namespace Sudoku.Common
{
/// <summary>
/// 数独解决方法实例
/// </summary>
public interface ISudokuSolution
{
/// <summary>
/// 设置或获取要解决的数独
/// </summary>
ISudoku Sudoku { get; set; }
/// <summary>
/// 解决数独
/// </summary>
/// <returns>解决完成的数独</returns>
ISudoku Solve();
/// <summary>
/// 检测该位置的点是否能放置
/// </summary>
/// <param name="row">行坐标</param>
/// <param name="col">列坐标</param>
/// <param name="value">值</param>
/// <returns>如果能放置则返回true</returns>
bool CanSet(byte row, byte col,byte value);
/// <summary>
/// 获取该位置放置的值集合
/// </summary>
/// <param name="row">行坐标</param>
/// <param name="col">列坐标</param>
/// <returns>放置值的集合</returns>
List<byte> CanSetValues(byte row, byte col);
}
}
为了简单起见,还有一些公用的函数或利用配置文件生成数独或数独解决方案的实例!
Sudoku.CodeMonk代码的实现逻辑比较清晰,用的挖洞法来生成数独的!没有写什么具体的数独解决方法。撤销和重复使用Stack做的,没有什么Command模式,觉得比较麻烦。保存和读取是拿xml序列化和反序列化做的。其他的都是穷举等笨方法!
比较复杂的一部分就只能算是WinForm项目里的GDI+操作,自定义控件等。
为了让窗体看起来更Metro一些,我找了些微软官方的WP开发图标。并自定义了一个PicButton,有点小动画的效果(小动画哈)。
复杂一点就是自定义的SudokuLabel,具体的话看代码吧!
Release包下载:sudoku-release.zip
源码下载:https://files.cnblogs.com/wushilonng/Sudoku.zip
Codeplex地址:http://longsudoku.codeplex.com/
其他:
(1)自定义背景,删除掉目录下的background.jpg就会回到默认背景,放一个background.jpg到目录下就是背景了!
(2)Ctrl+Z撤销,Ctrl+Y重复,Ctrl+O打开,Ctrl+S保存,Ctrl+N新建,Ctrl+H辅助解答,Ctrl+R重置!
(3)右侧的几个数是用来说明当前格子里可以的填写的哪些数。
(4)所谓的小动画就是图标稍稍转一下!
(5)默认难度是1级(比较弱智),还没做难度调节,需要改代码(囧)。