文字で簡単な図形を表現するプログラム

正奇数nを与えて「*」「/」で図形を描くプログラムをつくる時の考え方をみてみよう。
ただし,一辺の長さがの正方形で,例えばn=9の時は次のような図形とする。
*********
/*******+
//*****++
///***+++
////*++++

1.n=9の時だけ使えるプログラムを考えて図形を描いてみよう。

プログラムを書く前に,日本語でこの作業を書いてみると次のようになる

「*」を9個書きなさい
「/」を1個書きなさい 「*」を7個書きなさい 「+」を1個書きなさい 改行しなさい
「/」を2個書きなさい 「*」を5個書きなさい 「+」を2個書きなさい 改行しなさい
「/」を3個書きなさい 「*」を3個書きなさい 「+」を3個書きなさい 改行しなさい
「/」を4個書きなさい 「*」を1個書きなさい 「+」を4個書きなさい 改行しなさい

となる。これをそのままプログラムにすると次のようになるが,汎用性がまったくないプログラムが出来上がる。

public class XXXX {
    public static void main(String[] args) {
        XXXX mainprg = new XXXX();
    }
   
    XXXX() {
        System.out.printf("*********\n");
        System.out.printf("/*******+\n");
        System.out.printf("//*****++\n");
        System.out.printf("///***+++\n");
        System.out.printf("////*++++\n");
    }
}

/*実行結果

*********
/*******+
//*****++
///***+++
////*++++

*/

個々の作業が何行目なのかわかるようにすると

(1行目)「*」を9個書きなさい
(2行目)「/」を1個書きなさい 「*」を7個書きなさい 「+」を1個書きなさい 改行しなさい
(3行目)「/」を2個書きなさい 「*」を5個書きなさい 「+」を2個書きなさい 改行しなさい
(4行目)「/」を3個書きなさい 「*」を3個書きなさい 「+」を3個書きなさい 改行しなさい
(5行目)「/」を4個書きなさい 「*」を1個書きなさい 「+」を4個書きなさい 改行しなさい

となる。変数化するのに都合よいように,1行目でなく0行目から数え始めると

(0行目)「/」を0個書きなさい 「*」を9個書きなさい 「+」を0個書きなさい 改行しなさい
(1行目)「/」を1個書きなさい 「*」を7個書きなさい 「+」を1個書きなさい 改行しなさい
(2行目)「/」を2個書きなさい 「*」を5個書きなさい 「+」を2個書きなさい 改行しなさい
(3行目)「/」を3個書きなさい 「*」を3個書きなさい 「+」を3個書きなさい 改行しなさい
(4行目)「/」を4個書きなさい 「*」を1個書きなさい 「+」を4個書きなさい 改行しなさい

となり,これをプログラムにすると次のようになる。

public class XXXX {
    public static void main(String[] args) {
        XXXX mainprg = new XXXX();
    }
   
    XXXX() {
        int j;
        for (j=0;j<0;j++) System.out.printf("/");
        for (j=0;j<9;j++) System.out.printf("*");
        for (j=0;j<0;j++) System.out.printf("+");
        System.out.printf("\n");
        for (j=0;j<1;j++) System.out.printf("/");
        for (j=0;j<7;j++) System.out.printf("*");
        for (j=0;j<1;j++) System.out.printf("+");
        System.out.printf("\n");
        for (j=0;j<2;j++) System.out.printf("/");
        for (j=0;j<5;j++) System.out.printf("*");
        for (j=0;j<2;j++) System.out.printf("+");
        System.out.printf("\n");
        for (j=0;j<3;j++) System.out.printf("/");
        for (j=0;j<3;j++) System.out.printf("*");
        for (j=0;j<3;j++) System.out.printf("+");
        System.out.printf("\n");
        for (j=0;j<4;j++) System.out.printf("/");
        for (j=0;j<1;j++) System.out.printf("*");
        for (j=0;j<4;j++) System.out.printf("+");
        System.out.printf("\n");
    }
}

/*実行結果

*********
/*******+
//*****++
///***+++
////*++++

*/

この図形を描く作業は0行目から4行目まであるが,その作業は次のような作業の繰り返しである。

for (j=0;j<◆;j++) System.out.printf("/");
for (j=0;j<■;j++) System.out.printf("*");
for (j=0;j<◆;j++) System.out. printf("+");
printf("\n");

一般法則化するために i 行目について記述すると次のようになる

( i 行目)「/」を i 個書きなさい 「*」を (9-2*i) 個書きなさい 「+」を i 個書きなさい。 改行しなさい。

これを用いてプログラム化すると

public class XXXX {
    public static void main(String[] args) {
        XXXX mainprg = new XXXX();
    }
   
    XXXX() {
        int i,j;
        for (i=0;i<5;i++) {
            for (j=0;j<i;j++) System.out.printf("/");
            for (j=0;j<9-2*i;j++) System.out.printf("*");
            for (j=0;j<i;j++) System.out.printf("+");
            System.out.printf("\n");
        }
    }
}

/*実行結果

*********
/*******+
//*****++
///***+++
////*++++

*/


2.次にn=7の時だけ使えるプログラムを考えて図形を描いてみよう。

(0行目)「/」を0個書きなさい 「*」を7個書きなさい 「+」を0個書きなさい 改行しなさい
(1行目)「/」を1個書きなさい 「*」を5個書きなさい 「+」を1個書きなさい 改行しなさい
(2行目)「/」を2個書きなさい 「*」を3個書きなさい 「+」を2個書きなさい 改行しなさい
(3行目)「/」を3個書きなさい 「*」を1個書きなさい 「+」を3個書きなさい 改行しなさい

0行目から3行目まであるが,一般法則化するためにi行目について記述すると

( i 行目)「/」を i 個書きなさい 「*」を (7-2*i) 個書きなさい 「+」を i 個書きなさい。 改行しなさい。

これをプログラム化すると

public class XXXX {
    public static void main(String[] args) {
        XXXX mainprg = new XXXX();
    }
   
    XXXX() {
        int i,j;
        for (i=0;i<4;i++) {
            for (j=0;j<i;j++) System.out.printf("/");
            for (j=0;j<7-2*i;j++) System.out.printf("*");
            for (j=0;j<i;j++) System.out.printf("+");
            System.out.printf("\n");
        }
    }
}

/*実行結果

*******
/*****+
//***++
///*+++

*/



3.一般的に正奇数nに対して使えるプログラムを考えて図形を描いてみよう。

作業する行数はn=9の時5行,n=7の時4行,n=5の時3行....となるので,行数nlinesは(n+1)/2
となる

(0行目)「/」を0個書きなさい 「*」をn個書きなさい 「+」を0個書きなさい 改行しなさい
(1行目)「/」を1個書きなさい 「*」をn-2*1個書きなさい 「+」を1個書きなさい 改行しなさい
(2行目)「/」を2個書きなさい 「*」をn-2*2個書きなさい 「+」を2個書きなさい 改行しなさい
(3行目)「/」を3個書きなさい 「*」をn-2*3個書きなさい 「+」を3個書きなさい 改行しなさい
                                    :
((nlines-1)行目)「/」をnlines-1個書きなさい 「*」をn-2*(nlines-1)個書きなさい 「+」をnlines-1個書きなさい 改行しなさい

一般的なi行目の作業は

( i 行目)「/」を i 個書きなさい 「*」を n-2*i 個書きなさい 「+」を i 個書きなさい 改行しなさい

これをプログラム化すると

import java.util.*;  // StringTokenizer
import java.io.*;    // BufferedReader

public class XXXX {
    public static void main(String[] args) {
        XXXX mainprg = new XXXX();
    }
   
    XXXX() {
        int nodd;  /*与えられた奇数*/
        int nlines;/*行数*/
        int i,j;

        nodd=getInt("正奇数を入力してね : ");
        nlines=(nodd+1)/2;
        for (i=0;i<nlines;i++) {
            for (j=0;j<i;j++) System.out.printf("/");
            for (j=0;j<nodd-2*i;j++) System.out.printf("*");
            for (j=0;j<i;j++) System.out.printf("+");
            System.out.printf("\n");
        }
    }

    private int getInt(String prompt){
        BufferedReader bffrd = new BufferedReader(new InputStreamReader(System.in));
        int ret=0;
        System.out.print(prompt);
        try {
            ret = Integer.valueOf(bffrd.readLine()).intValue();
        }
        catch(IOException e) {
            System.out.println("IO Error");
            System.exit(1);
        }
        return ret;
    }
}

/*実行結果

正奇数を入力してね : 13
*************
/***********+
//*********++
///*******+++
////*****++++
/////***+++++
//////*++++++

*/