[BaekJoon/백준] 5단계 "실습1"

Hevton·2020년 8월 31일
0

이에 해당하는 문제들은 10039번, 5543번, 10817번, 2523번, 2446번, 10996번으로 총 6문제이다. 이 중 2446번과 10996번이 생각을 많이 요구하는 문제로 두 문제 다 이중포문을 요구하는 문제였다.

∙ 2446번

import java.io.BufferedReader;
import java.io.BufferedWriter;
import java.io.InputStreamReader;
import java.io.OutputStreamWriter;
import java.util.StringTokenizer;

public class Main {
    public static void main(String args[]) {
        BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
        BufferedWriter bw = new BufferedWriter(new OutputStreamWriter(System.out));
        StringTokenizer tokenizer = null;
        int N = 0;
        try {
            N = Integer.parseInt(br.readLine());

            for(int i = N; i > 1; i --)
            {
                for(int k = 0 ; k < N-i ; k++)
                {
                    bw.write(" ");
                }
                for(int j = 2*i-1; j>0; j--)
                {
                    bw.write("*");
                }
                bw.write("\n");
            }

            for(int i = 1 ; i < N+1; i++)
            {
                for(int k = N ; k > i; k--)
                {
                    bw.write(" ");
                }
                for(int j = 0; j < 2*i-1 ; j++)
                {
                    bw.write("*");
                }
                bw.write("\n");
            }
            br.close();
            bw.flush();
            bw.close();
        } catch (Exception e) {
        }
    }
}

위에 보다시피 코드가 깨끗하지도 않고 너저분하고 내가 코딩을 잘 하는것도 아니지만 그래도 이중포문을 구현할 때의 방법에 있어서 개인적인 생각을 정리하자면, 이중포문에서 바깥포문은 행 반복에 대한 구성, 안의 포문은 열 반복에 대한 구성이라고 생각하면 이해가 쉽다.
그러면 대충 어떻게 구성을 해 나갈지 감이 조금 올 수 있다. 우선 바깥포문을 구성한 뒤에는, 안 포문에 대해서 생각할 때 첫번째 경우와 마지막 경우를 생각하면 쉽다. 이중포문의 제일 첫 시작의 경우와 제일 끝 경우를 말하는 것이다.

  *
 **
***

입력이 3일때 이런 별찍기가 있을 때, 규칙이 점점 늘어나는 별이고 별다른 그 이상의 규칙은 없으므로 바깥 포문은 전체 N(여기서는 3)회, 안쪽 포문은 공백포문 하나, 그리고 별 포문 하나면 되겠다.

for(int i = 1 ; i < N+1; i++)
{
    for(int k = N ; k > i; k--)
    {
        bw.write(" ");
    }
    for(int j = 0; j < 2*i-1 ; j++)
    {
        bw.write("*");
    }
    bw.write("\n");
}

공백이 어떻게 출력되어야 하냐를 생각해 보자면, 제일 첫번째에는 N-1번 출력되어야 하고, 제일 마지막에는 출력이 되면 안된다는 것을 생각하고, 바깥 포문의 변수 i의 처음과 끝( 첫번째 경우는 i = 1, 마지막 경우는 i = N)을 생각하여 안쪽 포문의 처음과 마지막 경우를 잡아줄 수 있을 것이다. 그리고 이에 더해 i 가 어떻게 변하느냐 (위 코드의 경우, 점점 증가하는 ++ )를 생각하며 안쪽 포문의 비교문이나 증감문을 잡아줄 수 있다.

<정리>

  1. 이중포문에서 바깥포문은 행 반복, 안 포문은 열 반복이라고 생각하면 이해가쉽다.
  2. 이중포문에서는, 제일 첫번째와 제일 마지막 경우를 생각하면 쉽다.
    (바깥포문의 첫번째 경우와 안쪽 포문의 첫번째 경우에 연관성을 두고, 바깥 포문의 마지막 경우와 안쪽 포문의 마지막 경우의 연관성을 생각한 뒤 변수의 증감상황을 고려하여 안쪽 포문을 구현해준다)

∙ 10996번

import java.io.BufferedReader;
import java.io.BufferedWriter;
import java.io.InputStreamReader;
import java.io.OutputStreamWriter;
import java.util.StringTokenizer;

public class Main {
    public static void main(String args[]) {
        BufferedReader br = new BufferedReader(new InputStreamReader(System.in));
        BufferedWriter bw = new BufferedWriter(new OutputStreamWriter(System.out));
        StringTokenizer tokenizer = null;
        int N = 0;
        try {
            N = Integer.parseInt(br.readLine());
            if(N==1)
                bw.write("*");
            else {
                for (int i = 0; i < N; i++) {
                    for (int j = 1; j < N + 1; j++) {
                        if (j % 2 == 1)
                            bw.write("*");
                        else
                            bw.write(" ");
                    }
                    bw.write("\n");
                    for (int j = 1; j < N + 1; j++) {
                        if (j % 2 == 1)
                            bw.write(" ");
                        else
                            bw.write("*");
                    }
                    bw.write("\n");
                }
            }
            br.close();
            bw.flush();
            bw.close();
        } catch (Exception e) {
        }
    }
}

해당 문제의 규칙성을 생각해 바깥 포문을 먼저 잡았다. 1입력일때 1줄, 2입력일때 4줄, 3입력일때 6줄, 4입력일때 8줄인 상황을 보아하니
전체 포문의 경우를 N*2로 잡아도 되겠지만, 나는 전체 경우를 N으로 잡았다. 왜냐고? 나는 안쪽 포문의 역할을 한줄로 둔 게 아니라, 두 줄로 두었기 때문이다. 그림의 규칙성을 보아하니 두 줄 단위로 묶어서 반복됨을 볼 수 있다. 따라서 두 줄 단위를 안쪽 포문으로 두겠다고 생각했고, 바깥 포문은 따라서 N번으로 잡게 된 것이다.

결국 이중포문은 내가 구현하는 것. 바깥 포문이 행이고 안 포문이 열이라고 해서, 16줄이니 바깥포문은 16번 반복되어야 할 필요는 없다.

어떤 규칙으로 나누냐에 따라서 다르게 구현할 수 있다는 것이다.

profile
놀만큼 놀았다.

0개의 댓글