728x90
728x90
  1. 코드를 좌우로 정렬해준다
<html>
    <head>
        <meta charset = "utf-8">
        <title>Document</title>
        <link href = "css/main.css" rel = "stylesheet">
    </head>
    <body class="backgroundimagesea">
        <div class= "container">
            <div class="header"> </div>
            <div class="left-menu"></div><div class="right"></div>
            <div class="footer"></div>
        </div>
    </body>
</html>
  1. css에서 Inline block 설정을 해준다
.left-menu {
    width:20%;
    height:400px;
    background-color: rgba(12, 50, 242, 0.5);
    display: inline-block;

    
}

.right {
    width:80%;
    height:400px;
    background-color: rgba(40, 112, 242, 0.5);
    display: inline-block;
}

.footer {
    width: 100%;
    height: 50px;
    background-color: rgba(12, 112, 242, 0.7);

}

위의 코드는 박스를 만들어 왼쪽으로 정렬시키는 코드다.

display 속성만 inline-block 으로 조정하면 가로로 배치가 가능하다.

inline-block은 “내 폭과 높이만큼 자리차지하게 해주세요” 라는 뜻이다.

간편하지만 태그 사이에 스페이스바 공백이 있다면 그대로 보여준다

→ 가로로 정렬하려면 태그 사이의 공백도 제거해줘야 함

  • 공백제거하는 방법
  1. 주석처리 기호 사용하기
  2. 부모의 폰트사이즈를 0으로 만들기

정상적으로 된다

 

💡 부모 태그로부터 inherit되는 속성은 중요도가 가장 낮다

 

<html>
    <head>
        <meta charset = "utf-8">
        <title>Document</title>
        <link href = "css/main.css" rel = "stylesheet">
    </head>
    <body class="backgroundimagesea">
        <div class= "container">
            <div class="header"> </div>
            <div class="left-menu"></div><div class="right"></div>
            <div class="footer">
                <P>찬란한 미래를 위하여 </P.>
            </div>
           
        </div>
    </body>
</html>

이렇게 글자를 쓰면 이상하게 나온다. 해결책은 Vertical-allign을 사용해야 한다.

중앙 정렬을 하는 역할.

inline을 사용하면 Baseline을 따르게 되기 때문이다.

  1. 코드를 좌우로 정렬해준다
<html>
    <head>
        <meta charset = "utf-8">
        <title>Document</title>
        <link href = "css/main.css" rel = "stylesheet">
    </head>
    <body class="backgroundimagesea">
        <div class= "container">
            <div class="header"> </div>
            <div class="left-menu"></div><div class="right"></div>
            <div class="footer"></div>
        </div>
    </body>
</html>
  1. css에서 Inline block 설정을 해준다
.left-menu {
    width:20%;
    height:400px;
    background-color: rgba(12, 50, 242, 0.5);
    display: inline-block;

    
}

.right {
    width:80%;
    height:400px;
    background-color: rgba(40, 112, 242, 0.5);
    display: inline-block;
}

.footer {
    width: 100%;
    height: 50px;
    background-color: rgba(12, 112, 242, 0.7);

}

위의 코드는 박스를 만들어 왼쪽으로 정렬시키는 코드다.

display 속성만 inline-block 으로 조정하면 가로로 배치가 가능하다.

inline-block은 “내 폭과 높이만큼 자리차지하게 해주세요” 라는 뜻이다.

간편하지만 태그 사이에 스페이스바 공백이 있다면 그대로 보여준다

→ 가로로 정렬하려면 태그 사이의 공백도 제거해줘야 함

  • 공백제거하는 방법
  1. 주석처리 기호 사용하기
  2. 부모의 폰트사이즈를 0으로 만들기

정상적으로 된다

<aside> 💡 부모 태그로부터 inherit되는 속성은 중요도가 가장 낮다

</aside>

<html>
    <head>
        <meta charset = "utf-8">
        <title>Document</title>
        <link href = "css/main.css" rel = "stylesheet">
    </head>
    <body class="backgroundimagesea">
        <div class= "container">
            <div class="header"> </div>
            <div class="left-menu"></div><div class="right"></div>
            <div class="footer">
                <P>찬란한 미래를 위하여 </P.>
            </div>
           
        </div>
    </body>
</html>


이렇게 글자를 쓰면 이상하게 나온다. 해결책은 Vertical-allign을 사용해야 한다.

중앙 정렬을 하는 역할.

inline을 사용하면 Baseline을 따르게 되기 때문이다.

728x90
300x250
728x90
728x90

항해99 1주차 과제이다.

 

  • 컴퓨터는 0과 9 사이의 서로 다른 숫자 3개를 무작위로 뽑습니다. (ex) 123, 759
  • 사용자는 컴퓨터가 뽑은 숫자를 맞추기 위해 시도합니다.
  • 컴퓨터는 사용자가 입력한 세자리 숫자에 대해서, 아래의 규칙대로 스트라이크(S)와 볼(B)를 알려줍니다.
    • 숫자의 값과 위치가 모두 일치하면 S
    • 숫자의 값은 일치하지만 위치가 틀렸으면 B
  • 기회는 무제한이며, 몇번의 시도 후에 맞췄는지 기록됩니다.
  • 숫자 3개를 모두 맞춘 경우, 게임을 종료합니다.

 

1. Readline 불러와준다

const readline = require('readline').createInterface({
	input: process.stdin,
	output: process.stdout
};

Readline같은 경우에는 내가 지금 구덩이 파고 있는 주제 중 하나이다.

아마 오늘 내로 1차적 삽질리포트가 올라올 것이다.

2. 배열을 지정한다

var answer = []

이 배열은 나중에 랜덤값을 저장할 때 사용해줄 것이다

3.랜덤한 숫자 생성하기

 var answer = [];
  while(answer.length < 3){
      var randomNum = Math.floor(Math.random()*10); 
      if(answer.indexOf(randomNum) > -1) continue;
      answer.push(randomNum);
  }

위 코드에서는 랜덤으로 숫자를 생성해 생성된 숫자가 4개 미만이라면 새로운 숫자가 생성되고,

중복되지 않는다고 하면 결괏값인 randomNum 에 저장이 된다.

조금 더 자세히 알아보도록 하자

  • 생성되는 숫자 제어하기
  while(answer.length < 3){

만약의 answer 배열의 길이가 3보다 작다면 ~ 으로 시작해서 작동하는 코드이다.

answer 배열의 길이가 3개 이상이라면 멈추게 된다

  • 숫자를 정수화한 후 Randomnum에 넣기
 var randomNum = Math.floor(Math.random()*10); 

이때 math.random()으로 숫자를 생성하고,

이 숫자의 범위는 0~1이기 때문에 *10을 해줘서 1~10으로 바꿔준다.

그 후 Math.floor로 소숫점을 떨궈주고, randomNum으로 정의해준다.

  • 코드의 중복 확인하기
      if(answer.indexOf(randomNum) > -1) continue;

indexof: 지정된 요소의 인덱스를 검색하는 javascript의 내장 메서드이다.

호출한 배열에서 첫번째로 일치하는 요소의 인덱스변환, 일치하는 요소가 없는 경우 -1 을 반환한다.

만약 2번째 숫자가 같았으면 해당숫자의 인덱스인 1이 반환되고,

첫번째 숫자가 같았으면 해당 숫자의 인덱스인 0이 반환된다.

-1보다 작으면 continue로 계속해준다

indexof도 곧 포스팅할 예정이다!.

  • 중복이 아니라면
   answer.push(randomNum);

randomNum에 answer가 들어가게 된다

4. 세자리 숫자 입력받고 사용자 입력의 중복/글자수 이상 처리하기

 function playGame() {
    readline.question('세자리 숫자를 입력하세요.', (playerInput) => {
      count++;
      if(playerInput.length !== 3 || new Set(playerInput).size !== 3){
          console.log("세자리의 서로 다른 숫자를 입력하세요.");
          playGame();
          return;
      }

readline를 이용하여 세자리 숫자를 입력받았다.

그러나 만약 세 자리 숫자 안에 중복된 숫자가 있거나, 4자리라면 어떻게 되는 걸까?

당연히 프로그램 진행에 문제가 생긴다.

자세히 뜯어보자.

세 자리 숫자 입력받고 입력받을 때 마다 시도횟수 하나씩 증가시키기

 function playGame() {
    readline.question('세자리 숫자를 입력하세요.', (playerInput) => {
      count++;

나는 playGame이라는 함수를 사용하기로 했다

제일 먼저 readline.question으로 사용자의 입력을 받았다

실행 결과의 이 부분이라고 생각하면 될 것 같다.

사용자가 입력한 값은 콜백 함수의 매개변수인 playerInput에 저장된다.

한번 입력을 받을 때 마다 count 횟수를 1씩 늘려준다

이는 마지막에 시도 횟수를 출력할때 사용된다

  • 사용자 입력의 중복이 있거나 길이가 3이 아니라면
    if(playerInput.length !== 3 || new Set(playerInput).size !== 3){
          console.log("세자리의 서로 다른 숫자를 입력하세요.");
          playGame();
          return;
      }

논리 OR 연산자

두 개의 피연산자중 하나 이상이 True이상인지를 확인하고, 결과로 True를 반환한다.

  • 왼쪽 피연산자를 평가한 결과가 True이면 오른쪽 피연산자 평가 x 그냥 바로 True반한
  • 왼쪽 피연산자를 평가한 결과가 False 이면 오른쪽 피연산자 평가하고 그 결과를 반환함

(추후 포스팅해볼 내용이 더 늘어나버렸네…;;

이걸 어떻게 적용했냐면

    if(playerInput.length !== 3 || new Set(playerInput).size !== 3){

이 상황에서 playerInput.length이 3이 아니라면, 뒤에 중복 여부 결과는 보지 않고 바로 True를 반환한다.

숫자가 3개도 아닌데 굳이 중복 볼 필요가 있냐는거다.

그래서 먼저 앞의 숫자 갯수를 확인해본 후 playerInput을 Set 형태로 바꿔준다

*set은 중복이 존재할 수 없다

중복이 없는 상태에서 숫자의 갯수가 3개가 맞는지 확인하는 과정이였다.

논리 OR 연산자 쓰는 게 습관이 되어가고 있다 ! &ㅠ&

5. 기본 값 세팅하기

      var strike = 0;
      var ball = 0;
      var checkResult = Array(3).fill(0);

strike 카운트와 Ball 카운트를 초기화해준다.

그리고 Array(3).fill(0)이라는 게 보이는데 이는 길이간 3인 배열을 생성하고, 그 배열의 모든 요소를 0으로 채우는 역할을 한다.

Array 생성자 함수에 문자 3을 인수로 넣어 배열의 길이를 설정하고, fill 메서드를 조합해서 쓰여진다.

나는 이것을 세 자리 수에 각각 비교하도록 구성해보려 하였다.

  • array와 Fill을 사용하지 않고 작성한다면??

직접 배열 리터럴을 사용하여 배열을 생성하고 요소에 초기값을 할당한다

var checkResult = [0, 0, 0];

배열 생성 후에 반복문이나 인덱스 접근을 통해 각 요소에 초기값을 할당한다.

var checkResult = [];
for (var i = 0; i < 3; i++) {
  arr[i] = 0;
}

빈 배열을 생성한 후에 반복문을 사용하여 각 요소에 초기값 0을 할당하는 법.

배열의 크기가 커지면 이 방향을 사용하여야 할듯

away.from 메서드를 사용하여 배열을 생성하고 초기값을 할당한다

var arr = Array.from({ length: 3 }, () => 0);

이러한 방법으로도 쓸 수 있다. array.fill이랑 다른 점이라면 여러 개의 매개변수를 받을 수 있다 정도?

  1. 현재 요소의 값
  2. 현재 요소의 인덱스
  3. 생성된 배열의 전체 길이

를 받을 수 있다.

비어있는 자리에는 value, index가 들어있다

추후 좀 더 공부해보고 이 주제만 단독으로 포스팅해보도록 하겠다 !

6. 볼과 스트라이크 구성/ 표현

   for(var i=0; i<3; i++){
          if(answer[i] == playerInput[i]){
              checkResult[i] = 2;
          } else if(answer.indexOf(parseInt(playerInput[i])) > -1){
              checkResult[i] = 1;
          }
      }

i를 0으로 두었고, 세 자리 숫자이기에 세 번만 할 수 있도록 제한해준다.

한번 실행될따마 i에 하나씩 더해진다

  • 스트라이크 구현
          if(answer[i] == playerInput[i]){
              checkResult[i] = 2;

만약 정답의 n번째 인덱스에 있는 숫자가 입력값의 n번째 인덱스에 있는 숫자와 같다면

checkResult[i]가 2가 된다

즉 strike 를 나타내는 표현으로 2를 둔 것이다

  • 볼 구현
          } else if(answer.indexOf(parseInt(playerInput[i])) > -1){
              checkResult[i] = 1;
          }

스트라이크는 조금 감이 잡혔는데 볼은 어떻게 구현해야 할 지 감이 잘 안 잡혔었다.

그래서 중복 찾기에서 진행했던 방식을 조금 활용해보기로 헀다.

playerinput이 지금 사용자가 입력한 문자열을 가지고 있기에 parseInt로 정수로 변환한다.

Indexof 메서드는 배열에서 특정값을 검색하고, 검색된 값의 첫 번째 인덱스를 보낸다.

만약에 Indexof 값이 -1을 넘는다면 특정 인덱스에서 겹친다는 것이다

따로 떼놓고 본다면, 어? 저렇게 되면 스트라이크도 볼이 될 수 있는 거 아니야? 라고 할 수 있는데

   for(var i=0; i<3; i++){
          if(answer[i] == playerInput[i]){
              checkResult[i] = 2;
          } else if(answer.indexOf(parseInt(playerInput[i])) > -1){
              checkResult[i] = 1;
          }
      }

이렇게 전체를 보면 이해가 된다

if문에서 인덱스가 아예 같은건 다 스트라이크로 보내버리고

남은것들만 있기 때문이다

7.볼과 스트라이크 세기

  strike = checkResult.filter(x => x === 2).length;
  ball = checkResult.filter(x => x === 1).length;

checkresult.filter로 조건을 만족하는 요소들을 필터링하여 새로운 배열을 생성한다.

x는 현재 요소를 나타내는 매개변수이다

x가 2가 일치하는 경우로 배열을 만들어버리고 그 배열의 길이를 구하는 것이다.

strike,Ball을 숫자로 둔 이유가 그것이다

ball같은 경우에도 마찬가지다. result에 ball이 몇개가 있는지 확인하고 그 배열의 길이를 구해준다

  • 여기서 질문: 새로 생긴 배열은 어디에 저장되는가 ? 저장하긴 하는가?

→ 저장 안 된다. 그냥 쓰고 버림. strike에 저장되는건 새로 만든 배열의 길이일 뿐임.

→ 그럼 이거는 그냥 날리는 건가요? 필요가 없어서 뒤에 사용을 안 했다면 날려버리는거죠?

8. 결과 출력하기

    if(strike === 3){
          console.log("축하합니다! " + count + "번만에 맞췄습니다.");
          readline.close();
      } else {
          console.log(strike + "S " + ball + "B 입니다.");
          playGame();
      }
    });
  }

strike가 세 개면 종료 메세지를 출력한다.

세 개가 아니면 될 때 까지 출력해주고 스트라이크 갯수와 볼 갯수를 포함해 안내 메세지를 출력해준다.

그리고 Playgame 함수를 다시 출력해준다

 

 

구현화면

 

 

최종 코드

const readline = require('readline').createInterface({
    input: process.stdin,
    output: process.stdout
  });
  
  var answer = [];
  while(answer.length < 3){
      var randomNum = Math.floor(Math.random()*10); 
      if(answer.indexOf(randomNum) > -1) continue;
      answer.push(randomNum);
  }
  
  var count = 0;
  
  function playGame() {
    readline.question('세자리 숫자를 입력하세요.', (playerInput) => {
      count++;
  
      if(playerInput.length !== 3 || new Set(playerInput).size !== 3){
          console.log("세자리의 서로 다른 숫자를 입력하세요.");
          playGame();
          return;
      }
  
      var strike = 0;
      var ball = 0;
      var checkResult = Array(3).fill(0);
  
      for(var i=0; i<3; i++){
          if(answer[i] == playerInput[i]){
              checkResult[i] = 2;
          } else if(answer.indexOf(parseInt(playerInput[i])) > -1){
              checkResult[i] = 1;
          }
      }
  
      strike = checkResult.filter(x => x === 2).length;
      ball = checkResult.filter(x => x === 1).length;
  
      if(strike === 3){
          console.log("축하합니다! " + count + "번만에 맞췄습니다.");
          readline.close();
      } else {
          console.log(strike + "S " + ball + "B 입니다.");
          playGame();
      }
    });
  }
  
  playGame();
728x90
300x250

+ Recent posts