![](http://oshiete.xgoo.jp/images/v2/pc/qa/question_title.png?5a7ff87)
数独の解答を一発で出すプログラムを考えています。
自分が考えたプログラムは下記の通りです。
import java.util.Random;
public class NumberPlace {
public static void main(String[] args) {
int i, j, k, l, check=0, count=0, tmp;
int a[][] = new int [9][9];
Random rnd = new Random();
int ran;
for ( i=0; i<9; i++ )
for ( j=0; j<9; j++)
a[i][j] = 0;
count = 0;
for ( i=0; i<9; i++ ) {
for ( j=0; j<9; j++) {
ran = rnd.nextInt(9);
tmp = ran + 1;
check = 0;
for ( k=0; k<j; k++ )
if ( a[i][k] == tmp )
check = 1;
for ( k=0; k<i; k++ )
if ( a[k][j] == tmp )
check = 1;
for ( k=(i/3)*3; k<(i/3)*3+3; k++ )
for ( l=(j/3)*3; l<(j/3)*3+3; l++ )
if ( a[k][l] == tmp )
check = 1;
if ( check == 0 )
a[i][j] = tmp;
if ( check == 1 )
j--;
if ( count > 50000 )
break;
count++;
}
count = 0;
}
for ( i=0; i<9; i++) {
for ( j=0; j<9; j++ ) {
if ( a[i][j] < 10 ) {
System.out.print(" ");
}
System.out.print(a[i][j]);
}
System.out.print("\n");
}
}
}
これを実行すると、正しい数独の解が出来るまでに実行を20~30回。多い時は200回前後実行しないと出来ません。
実行結果(0は数独のルール上数字が入らない所)
9 3 6 5 4 1 7 8 2
1 7 4 2 9 6 5 3 0
5 2 8 7 3 0 0 0 0
2 1 5 3 7 8 4 6 9
8 6 3 4 1 9 2 7 5
4 9 7 6 5 2 1 0 0
7 5 1 8 6 4 9 2 3
3 8 2 9 0 0 0 0 0
6 4 9 1 2 5 8 0 0
これを一発で0がない状態にしたいのです。
因みにC言語だと下記のプログラムで一発で出るのですが。(前回質問したプログラム)
int main(void)
{
int i,j,k,l,chk=0,num=0,tmp,count=0;
int a[9][9];
srand((unsigned) time(NULL));
start:
count=0;
for(i = 0; i < 9; i++)
for(j = 0; j < 9; j++)
a[i][j]=0;
for(tmp=1;tmp<10;tmp++){
num=0;
while(num<9){
i = rand() % 9;
j = rand() % 9;
chk=0;
for(k=0;k<9;k++)
if(a[i][k]==tmp)chk=1;
for(k=0;k<9;k++)
if(a[k][j]==tmp)chk=1;
for(k=(i/3)*3;k<(i/3)*3+3;k++){
for(l=(j/3)*3;l<(j/3)*3+3;l++){
if(a[k][l]==tmp)chk=1;
}
}
if((chk==0)&&(a[i][j]==0)){
a[i][j]=tmp;
num++;
}
if(count%100==99){
count++;
for(i = 0; i < 9; i++)
for(j = 0; j < 9; j++)
if(a[i][j]==tmp)a[i][j]=0;
num=0;
}
if(count>10000) goto start;
count++;
}
}
for(i = 0; i < 9; i++){
for(j = 0; j < 9; j++){
printf("%d ",a[i][j]);
}
printf("\n");
}
return 0;
}
このプログラムを実行すると一発で解答が出ます。
上のJavaプログラムを下のプログラムのようにするにはどうしたら良いでしょうか。
No.2ベストアンサー
- 回答日時:
簡単な方法は…。
Cのもともとの、問題作成関数あるよね?
これをcreate()と呼ぶことにする。
void create(){
for(){
…
…
if(){goto start;}
}
}
となってるよね。
これを、
GOTO文を消す方向で書き直すと、
void A(){
while(true){
if(create()){break;}//完成したら終了
}
}
boolean create(){
for(){
…
…
if(){return false;}//問題が未完成ならfalse
}
return true;//完成ならtrue
}
ローカル変数は適宜、"グローバルな"位置に移してね。
これでうまくいくんじゃないかな?
上記のように「関数の2重化」を用いないで、
1つの関数だけで、制御構造を工夫してなんとかするやりかたもあるけど、
ややこしいかも。
No.1
- 回答日時:
を参考にしてどうなったの?
回答ありがとうございます。
前の質問で回答して下さった方々の方法もやってみましたが、上手くいきませんでした。
因みに、前の質問でchie65535さんのプログラムをJavaに変えようとしましたが、無限ループに入ってしまい、上手くいきませんでした。
質問したC言語のプログラムを自分なりにJavaプログラム直したら、下記のようになりました。
import java.util.Random;
public class NumberPlaceA {
public static void main(String[] args) {
int i, j, k, l, check = 0, num = 0, count = 0, tmp;
int a[][] = new int [9][9];
Random rnd = new Random();
int ran;
count=0;
for(i = 0; i < 9; i++)
for(j = 0; j < 9; j++)
a[i][j]=0;
for(tmp=1;tmp<10;tmp++){
num=0;
start:
while(num<9){
ran = rnd.nextInt(9);
i = ran;
j = ran;
check=0;
for(k=0;k<9;k++)
if(a[i][k]==tmp)check=1;
for(k=0;k<9;k++)
if(a[k][j]==tmp)check=1;
for(k=(i/3)*3;k<(i/3)*3+3;k++){
for(l=(j/3)*3;l<(j/3)*3+3;l++){
if(a[k][l]==tmp)check=1;
}
}
if((check==0)&&(a[i][j]==0)){
a[i][j]=tmp;
num++;
}
if(count%100==99){
count++;
for(i = 0; i < 9; i++)
for(j = 0; j < 9; j++)
if(a[i][j]==tmp)a[i][j]=0;
num=0;
}
if(count>10000) break start;
count++;
}
}
for ( i=0; i<9; i++) {
for ( j=0; j<9; j++ ) {
if ( a[i][j] < 10 ) {
System.out.print(" ");
}
System.out.print(a[i][j]);
}
System.out.print("\n");
}
}
}
これを実行すると、
3 0 0 0 0 0 0 0 0
0 9 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 0
0 0 0 7 0 0 0 0 0
0 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 0 0
0 0 0 0 0 0 0 2 0
0 0 0 0 0 0 0 0 0
となります。
お探しのQ&Aが見つからない時は、教えて!gooで質問しましょう!
似たような質問が見つかりました
- C言語・C++・C# 質問です 下記のコードを分かりやすく解説お願いします 初心者です #include ‹stdio.h 3 2022/05/26 22:03
- C言語・C++・C# C言語プログラム変更 2 2022/12/21 15:03
- Ruby 【JAVA】数字をひし形に出力するプログラムについて 2 2022/07/11 23:32
- C言語・C++・C# プログラミング c言語 4 2023/03/07 01:05
- FX・外国為替取引 mql4のコンパイルエラー箇所の修正お願いします。 1 2023/03/15 16:14
- C言語・C++・C# C言語 3 2022/11/09 13:27
- C言語・C++・C# LU分解法のピボッティングについて(C言語/gcc-9) 3 2022/07/11 23:10
- Excel(エクセル) エクセルVBAでオブジェクトが必要です 2 2022/09/10 16:37
- C言語・C++・C# C言語のエラーについて 2 2022/07/11 13:56
- Java javaでのプログラム(配列)について質問です. 2 2022/10/14 22:27
関連するカテゴリからQ&Aを探す
デイリーランキングこのカテゴリの人気デイリーQ&Aランキング
-
ループ処理の際、最後だけ","を...
-
java キーボード入力された値の...
-
テキストボックスに入力された...
-
Java 配列<選挙>
-
総称型ArrayList<E>への参照...
-
繰り返しによる星印の出力
-
Java 入力した整数値の合計を、...
-
3桁のカウンター表示
-
3つの値の中間値を求める
-
javaで素数判断プログラム作成...
-
キーボードから10人分の点数を...
-
〔java〕 計算結果に0をつける...
-
countに実行した回数をいれたい...
-
javaで九九の表を作りたい
-
エラー(互換性の無い型)
-
Ctrl+Zが入力されると終了する...
-
論理演算子”||”またはの入力方法
-
(急いでいます)Javaで3回間違...
-
Java、2の0乗~10乗の表示
-
数値⇒漢数字変換 java
マンスリーランキングこのカテゴリの人気マンスリーQ&Aランキング
-
ループ処理の際、最後だけ","を...
-
java キーボード入力された値の...
-
Java、2の0乗~10乗の表示
-
コマンドライン引数の例外処理...
-
数値⇒漢数字変換 java
-
Ctrl+Zが入力されると終了する...
-
続・ZZZ,ZZZ,ZZ9形式の金額形式...
-
countに実行した回数をいれたい...
-
論理演算子”||”またはの入力方法
-
7つ数字を表示したら改行すると...
-
テキストボックスに入力された...
-
配列を逆順させて表示させる方...
-
繰り返しによる星印の出力
-
Java 入力した整数値の合計を、...
-
キーボードから10人分の点数を...
-
JAVAのfor文で困っています。
-
階乗の式
-
要素数が10の配列で、乱数0~9...
-
Java キーボードから負の数が入...
-
Randomメソッドの確率設定
おすすめ情報