학습일지_CodeSquad_MC_D2

VANS·2022년 1월 4일
0

2022 마스터즈 코스

목록 보기
2/9

22.01.04(화)

작성 목적 : 그날 학습한 내용중 스스로가 소화한 내용을 정리하기 위함

학습하는 방법을 학습하기


  공부를 하다보면, 혼자하든 남들과 같이하든 불안할때도 있고 지루할때도 있고 오늘따라 집중이 잘되는 날이 있기도 하다. 매 순간이 집중이 잘되면 얼마나 좋을까? 이번 수업때는 학습시 발생하는 불안함과 지루함을 극복하는 방법부터 가르쳐 주었다.

1. 학습의 상태 : 몰입 / 불안함 / 지루함

  • 몰입 : 실력과 작업 난이도가 비례하며 학습하기 좋은 상태 (실력 ⍺ 난이도)
  • 불안함 : 실력이 낮아 작업 난이도가 높게 느껴져 불안한 상태 (실력 ↓ 난이도 ↑)
  • 지루함 : 실력이 높아 작업 난이도가 낮게 느껴져 지루한 상태 (실력 ↑ 난이도 ↓)

2. 극복하기

  • 불안함
    1) 전문가(멘토등)나 도구등을 통해 실력을 높여 난이도를 따라잡는다.
    2) 큰 문제를 작은 문제로 분리하여 난이도를 낮춰 실력에 맞춘다.

  • 지루함
    1) 낯선 개발 환경(메모장)이나 다른 도구등을 통해 실력을 낮춰 난이도에 맞춘다.
    2) 구현순서를 바꾸던지 제약을 추가하여 난이도를 높여 실력에 맞춘다.

  결국, 불안함과 지루함을 극복하는 방법은 자기만의 실력과 학습의 난이도 사이에서 밸런스를 찾아가는것을 말하는것으로 이해했다. 하지만 불안함과 지루함은 여유면에서 완전 다르니, 극복 방법이 달라도 가능하다면 지루함에서 극복하는 쪽으로 노력하자. (실력을 키워 지루함을 느낄날이 올까..?ㅎㅎ)

Refactoring

(수업 내용 노출을 피하기 위해 클래스명은 임의로 수정하였습니다.)


기존코드

문제점
1. boolean 타입의 메소드이므로 if문이 굳이 필요하지 않았음.
2. 몇몇 코드는 앞선 코드를 활용하여 작성 가능하지만, 인지못하고 중복 구현함.
3. 인자의 타입이 통일되지 않아 재사용성이 떨어짐.

public class Ex1 {

    public boolean andGate(int inputA, int inputB) {
        if ((inputA == 1) && (inputB == 1)) {
            return true;
        }
        return false;
    }

    public boolean orGate(int inputA, int inputB) {
        if ((inputA == 1) || (inputB == 1)) {
            return true;
        }
        return false;
    }

    public boolean nandGate(boolean relayA, boolean relayB) {
        if ((relayA == true) && (relayB == true)) {
            return false;
        }
        return true;
    }

    public boolean xorGate(boolean relayA, boolean relayB) {
        if ((relayA != relayB)) {
            return true;
        }
        return false;
    }

    public static void main(String[] args) {
    }

}

Refactor

개선점
1. 불필요한 if문을 제거 -> 가독성을 높임.
2. 인자 타입을 boolean타입으로 통일하여 재사용성을 높이고 중복 구현내용을 제거함

public class Ex1 {

    public boolean and(boolean relayA, boolean relayB){
        return relayA && relayB;
    }

    public boolean or(boolean relayA, boolean relayB){
        return relayA || relayB;
    }

    public boolean not(boolean relay){
        return !relay;
    }

    public boolean nand(boolean relayA, boolean relayB){
        return not(and(relayA , relayB));
    }

    public boolean xor(boolean relayA, boolean relayB){
        return or(and(not(relayA),relayB), and(relayA, not(relayB)));
    }

}

기존코드

문제점
1. answer 값을 리턴하기 위한 기능을 별도 클래스에 구현되어 있었으나, 중복 구현함
2. 출력을 위해 메소드안에 println 기능을 추가함(지양해야함)

    public boolean[] halfadder(boolean relayA, boolean relayB) {
        boolean[] answer = {halfCarryAndGate(relayA, relayB), halfSumXorGate(relayA, relayB)};
        System.out.println(Arrays.toString(answer));
        return answer;
    }

    public boolean halfSumXorGate(boolean relayA, boolean relayB) {
        if ((relayA != relayB)) {
            return true;
        }
        return false;
    }

    public boolean halfCarryAndGate(boolean relayA, boolean relayB) {
        if ((relayA == true) && (relayB == true)) {
            return true;
        }
        return false;
    }

Refactor

개선점
1. 중복 구현되어 있던 기능을 타 클래스의 메소드를 활용함으로써 가독성을 높임

    Gate gate = new Gate();

    public boolean[] halfAdder(boolean relayA, boolean relayB) {
        boolean[] answer = new boolean[2];

        boolean carry = gate.and(relayA, relayB);
        boolean sum = gate.xor(relayA, relayB);

        answer[0] = carry;
        answer[1] = sum;

        return answer;
    }

기존코드

문제점
1. answer 배열의 길이를 정해주어 가변 연산이 불가능하게 하드코딩함
2. 출력을 위해 메소드안에 println 기능을 추가함(지양해야함)
3. 연산하기 위해 full...sum과 full...carry를 구하는 메소드를 따로 따로 구현하여 불필요한 중복 코딩을 만듬

    public boolean[] byteadder(boolean[] byteA, boolean[] byteB){
        boolean[] answer = new boolean[9];
        boolean carry = false;

        for (int i = 0; i < answer.length; i++) {
            if(i == 8){
                answer[i] = fullCarryAndGate(byteA[i-1], byteB[i-1], carry);
            }else {
                answer[i] = fullSumOrGate(byteA[i], byteB[i], carry);
                carry = fullCarryAndGate(byteA[i], byteB[i], carry);
            }
        }
        System.out.println(Arrays.toString(answer));
        return answer;
    }

Refactor

개선점
1. answer의 길이를 입력되는 relayA와 relayB의 배열길이에 따라 바뀔수 있게
getAnswerLength 메소드 추가 구현
2. relayA와 relayB의 배열길이가 서로 다를때 긴 배열 길이에 맞춰 연산될 수 있도록
relayConverter 메소드 추가 구현
2-1. System.arraycopy(relayA, 0, relay, 0, relayA.length);
의미는 relayA[0] 부터 relay[0]에 길이 relayA.lenght 만큼 복사된다는 의미이다.
처음 써보는 함수였다. 앞으로 쏠쏠하게 쓰일듯! 특히 연산할때!
3. 연산은 fullAdder 메소드만 기능하여 구현할 수 있도록 수정하여 가독성을 높임

    public boolean[] byteAdder(boolean[] relayA, boolean[] relayB) {
        int length = getAnswerLength(relayA, relayB);
        boolean[] answer = new boolean[length];
        
        boolean[] relayAA = relayConverter(relayA, length);
        boolean[] relayBB = relayConverter(relayB, length);
        
        boolean carry = false;
        boolean[] adder;

        for (int i = 0; i < answer.length; i++) {
            adder = fullAdder(relayAA[i], relayBB[i], carry);

            carry = adder[0];
            answer[i] = adder[1];
        }
        
        return answer;
    }
    
    private boolean[] relayConverter(boolean[] relayA, int length) {
        boolean[] relay = new boolean[length];
        System.arraycopy(relayA, 0, relay, 0, relayA.length);
		
        return relay;
    }

    private int getAnswerLength(boolean[] relayA, boolean[] relayB) {
        int relayALength = relayA.length;
        int relayBLength = relayB.length;

        int answerLength;
        if (relayALength > relayBLength) {
            answerLength = relayALength + 1;
        } else if (relayALength < relayBLength) {
            answerLength = relayBLength + 1;
        } else {
            answerLength = relayALength + 1;
        }
        return answerLength;
    }  

Test

(수업 내용 노출을 피하기 위해 클래스명은 임의로 수정하였습니다.)


테스트 코드

느낀점
1. 그룹 코드 리뷰를 통해 Test 코드 작성과 실행 방법을 배웠는데, 출력으로 확인하는것보다 훨씬 편리함.
2. assert000 다양한 단언문을 통해 예상 값과 출력값이 일치하는지 체크할 수 있음.
2-1. 단언문 : 코드에서 불변의 정확성을 확인하는 데 사용됨

import org.junit.jupiter.api.Test;

import static org.junit.jupiter.api.Assertions.*;

    @Test
    void Test1(){
        assertTrue(test1.an(true, true));
        assertFalse(test1.an(true, false));
        assertFalse(test1.an(false, true));
        assertFalse(test1.an(false, false));
    }
    
    @Test
    void Test2(){
        assertArrayEquals(new boolean[]{true,false}, sum.test2(true, true));
        assertArrayEquals(new boolean[]{false,true}, sum.test2(true, false));
        assertArrayEquals(new boolean[]{false,true}, sum.test2(false, true));
        assertArrayEquals(new boolean[]{false,false}, sum.test2(false, false));
    }
    
    @Test
    void Test3() {
        boolean[] A = {true, true, false, true, true, false, true, false};
        boolean[] B = {true, false, true, true, false, false, true, true};
        boolean[] answer = {false, false, false, true, false, true, false, false, true};

        assertArrayEquals(answer, sum.Sum(A, B));
    }

profile
코딩도 점진적 과부화

0개의 댓글