
| 親メニュー | 子メニュー | 説明 |
|---|---|---|
| File(&F) | ||
| Save(&S) | 数字テーブルを保存する | |
| Load(&L) | 数字テーブルとヒントを入力する | |
| SaveAll(&A) | 数字テーブルとヒントを保存する | |
| Exit(&X) | プログラムを終了する |
using System.IO; // for File, StreamReader
using System.Text; // for Encoding
class form01
{
[STAThread]
public static void Main()
{
MyForm mf = new MyForm();
Application.Run(mf);
}
}
|
private void SaveFile(object sender, EventArgs e)
{
StreamWriter writer;
string file, str;
int i, j;
SaveFileDialog saveDialog = new SaveFileDialog();
saveDialog.Title = "保存するファイルを選択してください";
saveDialog.Filter = "Number|*.num|すべてのファイル|*.*";
saveDialog.RestoreDirectory = true;
if (saveDialog.ShowDialog(this) == DialogResult.OK)
{
file = saveDialog.FileName;
writer = new StreamWriter(file, false, Encoding.GetEncoding("utf-8"));
for (i = 0; i < 9; i++)
{
str = "";
for (j = 0; j < 9; j++)
{ str += (char)(m_t[i, j] | 0x30); }
str = str.Replace('0', '.');
writer.WriteLine(str);
}
for (i = 0; i < 9; i++)
{
str = "";
for (j = 0; j < 9; j++)
{ str += (char)(m_ct[i, j] | 0x30); }
writer.WriteLine(str);
}
writer.Close();
}
saveDialog.Dispose();
}
|
...46.2.5 .465138.9 .7389..61 .5824.7.. ..79.512. 9..67854. 13..26984 7...59.12 .92184.57 |
private void LoadFile(object sender, EventArgs e)
{
string file, str;
int i, j;
OpenFileDialog openDialog = new OpenFileDialog();
openDialog.Title = "Number ファイルを選択してください";
openDialog.Filter = "Number|*.num|すべてのファイル|*.*";
if (openDialog.ShowDialog() == DialogResult.OK)
{
file = openDialog.FileName;
if (!File.Exists(file)) return; //ファイルの有無をチェック
for (i = 0; i < 9; i++)
{ for (j = 0; j < 9; j++)
{ m_t[i, j] = 0;
m_ct[i, j] = 0;
}
}
StreamReader reader = new StreamReader(file, Encoding.GetEncoding("utf-8"));
for (i = 0; i < 9; i++)
{ if ((str = reader.ReadLine()) == null) break;
str = str.Replace('.', '0');
for (j = 0; j < 9; j++)
{ m_t[i, j] = (int)(str[j] & 0xf);
if (m_t[i, j]==0) m_ct[i, j] = 1;
}
}
for (i = 0; i < 9; i++)
{ if ((str = reader.ReadLine()) == null) break;
if (str.Length<9) continue;
for (j = 0; j < 9; j++)
{ m_ct[i, j] = (int)(str[j] & 0xf); }
}
reader.Close();
}
openDialog.Dispose();
Debug(m_t);
Invalidate();
}
|
private void Exit(object sender, EventArgs e)
{ this.Close(); }
|
bool m_OK = false; //完成フラグ
// 完成を確認
private void Complete(object sender, EventArgs e)
{ int sum;
if (Error())
{ Invalidate();
return;
}
for (int i = 0; i < 9; i++)
{ sum = 0;
for (int j = 0; j < 9; j++) sum += m_t[i, j];
if (sum != 45) return;
sum = 0;
for (int j = 0; j < 9; j++) sum += m_t[j, i];
if (sum != 45) return;
}
m_OK = true;
Invalidate();
}
|
private void MyHandler(object sender, PaintEventArgs e)
{
・・・
if (m_OK)
{ Font f = new Font("MS ゴシック", 30);
g.DrawString("完成しました! \(^o^)/", f, Brushes.Red, new PointF(30F, 260F));
m_OK = false;
}
}
|
public bool Error()
{ int[] chk = new int[10];
int i,j,w;
bool flag = false;
for(i=0; i<9; i++)
{ for(j = 0; j < 10; j++) chk[j] = 0;
for(j = 0; j < 9; j++)
{ if (m_ct[i, j]!=0) m_ct[i, j] = 1;
chk[m_t[i, j]]++;
}
for(j = 0; j < 9; j++)
{
if (m_ct[i, j]>0 && m_ct[i, j]<7)
{
w = m_t[i, j];
if (w>0 && chk[w] > 1)
{ m_ct[i, j] = 6;
flag = true;
}
}
}
for(j = 0; j < 10; j++) chk[j] = 0;
for(j = 0; j < 9; j++) chk[m_t[j, i]]++;
for(j = 0; j < 9; j++)
{
if (m_ct[j, i]>0 && m_ct[j ,i]<7)
{
w = m_t[j, i];
if (w>0 && chk[w] > 1)
{ m_ct[j, i] = 6;
flag = true;
}
}
}
}
for (i = 0; i < 3; i++)
for (j = 0; j < 3; j++)
if (Err3(i*3, j*3)) flag = true;
return flag;
}
|
public bool Err3(int y, int x)
{ int[] chk = new int[10]; //3*3 で使われている数字
int i,j,w;
bool flag = false;
for(i=0; i<10; i++) chk[i] = 0;
for(i=0; i<3; i++)
for(j=0; j<3; j++)
chk[m_t[i+y, j+x]]++;
for(i=0; i<3; i++)
for(j=0; j<3; j++)
if (m_ct[i+y, j+x] > 0 && m_ct[i+y, j+x] < 7)
{ w = m_t[i+y, j+x];
if (w>0 && chk[w] > 1)
{ m_ct[i+y, j+x] = 6;
flag = true;
}
}
return flag;
}
|
private void Check(object sender, EventArgs e)
{ Error();
m_hint = false;
Invalidate();
}
|
private void Play(object sender, EventArgs e)
{
for(int y=0; y<9; y++)
for(int x=0; x<9; x++)
{ m_t[y, x] = m_b[y, x];
if (m_ct[y,x]!=0) m_ct[y, x] = 1;
}
Invalidate();
}
|
int[,,] m_ht = new int[9,9,10]; //Helpテーブル
int[,] m_ct = new int[9, 9]; //プレートの色テーブル
bool m_hint = false; //Hint Mode
private void Hint(object sender, EventArgs e)
{
SetHint();
m_hint = true;
Invalidate();
}
|
public void SetHint()
{ int x,y,k,wn;
for(y=0; y<9; y++)
for(x=0; x<9; x++)
{ if (m_ct[y,x]>4) m_ct[y,x] = 1;
for(k=0; k<10; k++) m_ht[y,x,k] = k;
}
for(y=0; y<9; y++)
for(x=0; x<9; x++)
{ wn = m_t[y,x];
if (wn!=0)
{ for(k=0; k<9; k++)
{ m_ht[y,k,wn] = 0; //y行から消す
m_ht[k,x,wn] = 0; //x列から消す
Del33(y,x);
}
}
}
}
|
public void Del33(int y, int x)
{ int i,j,yw,xw,n;
n = m_t[y,x];
yw = (y/3)*3;
xw = (x/3)*3;
for(i=0; i<3; i++)
for(j=0; j<3; j++) m_ht[yw+i,xw+j,n] = 0;
}
|
| 親メニュー | 説明 | |
|---|---|---|
| NewGame(&G) | ||
| Lebel-1(&A) | 初心者レベルの問題です | |
| Lebel-2(&B) | 初級者レベルの問題です | |
| Lebel-3(&C) | 中級者レベルの問題です | |
| Init(&R) | リセットして出題図に戻す | |
| Complete(&Q) | 問題が正しく作成できたことを確認する |
// Data 作成領域
int[,] restcol = new int[9, 10]; //縦列制限テーブル[col][num] = 0 : 埋めれる, 1 : 埋めれない
int[, ,] restblock = new int[3, 3, 10]; //ブロック制限テーブル[row/3][col/3][num] = 同上
|
public void Generate(int rate)
{
makeMahoujin();
for(int y=0; y<9; y++)
for(int x=0; x<9; x++) m_t[y, x] = m_b[y, x];
// m_t[y,x]=0 色=1 で穴抜きを設定
for(int y=0; y<9; y++)
for(int x=0; x<9; x++)
{
m_ct[y, x] = 0;
if (rand.Next(100) < rate)
{ m_t[y, x] = 0;
m_ct[y, x] = 1;
}
}
Invalidate();
}
|
public void makeMahoujin()
{ int i,j,k;
int row,col,num;
do //回答得られるまで繰り返し
{ //制限テーブル、回答テーブル初期化
for(i=0; i<9; i++)
for(j=0; j<9; j++)
m_b[i,j] = 0;
for(i=0; i<9; i++)
for(j=0; j<10; j++)
restcol[i,j] = 0;
for(i=0; i<3; i++)
for(j=0; j<3; j++)
for(k=0; k<10; k++)
restblock[i,j,k] = 0;
//埋めようとしてみます
for(row=0; row<9; row++)
{ //1行あたり 40回 挑戦。
for(i=0; i<40; i++)
{ if( num_tryfillrow(row)!=0 ) break; //埋めアルゴリズムここで変更
//else x[row]++; //つまった回数行ごとにカウント
}
//無理ぽ。最初からやり直し
if( i >= 40 ) break;
//1行埋まった。制限テーブル更新
for(col=0; col<9; col++)
{ num = m_b[row,col];
restcol[col,num] = 1;
restblock[row/3,col/3,num] = 1;
}
}
} while(row < 9);//最後の行まで埋まるまで繰り返し
}
//引数で渡された未完の行、空にして埋めなおす
//埋める数字をランダムで決定(0 失敗 1 成功)
public int num_tryfillrow(int row)
{
int k;
int col,num;
int[] kouho = new int[9];
int[] used = new int[10];
//どの数字既に埋めたかテーブル初期化
for(num=1; num<10; num++) used[num] = 0;
//左から順に埋めていく
for(col=0; col<9; col++){
//埋めれる数字を kouho に入れる
k = 0;
for(num=1; num<10; num++)
if( restcol[col,num] == 0 && restblock[row/3,col/3,num] == 0 && used[num] == 0 )
kouho[k++] = num;
//何も埋められない→失敗
if(k == 0) { return(0); }
//ランダムで数字を決定
num = kouho[rand.Next(k)];
m_b[row,col] = num;
used[num] = 1;
}
return(1); //成功
}
|
[Next Chapter ↓] Alpha 版の実行
[Previous Chapter ↑] Menu