[백준] 4659 비밀번호 발음하기 JavaScript

·2024년 5월 8일

문제

좋은 패스워드를 만드는것은 어려운 일이다. 대부분의 사용자들은 buddy처럼 발음하기 좋고 기억하기 쉬운 패스워드를 원하나, 이런 패스워드들은 보안의 문제가 발생한다. 어떤 사이트들은 xvtpzyo 같은 비밀번호를 무작위로 부여해 주기도 하지만, 사용자들은 이를 외우는데 어려움을 느끼고 심지어는 포스트잇에 적어 컴퓨터에 붙여놓는다. 가장 이상적인 해결법은 '발음이 가능한' 패스워드를 만드는 것으로 적당히 외우기 쉬우면서도 안전하게 계정을 지킬 수 있다.

회사 FnordCom은 그런 패스워드 생성기를 만들려고 계획중이다. 당신은 그 회사 품질 관리 부서의 직원으로 생성기를 테스트해보고 생성되는 패스워드의 품질을 평가하여야 한다. 높은 품질을 가진 비밀번호의 조건은 다음과 같다.

모음(a,e,i,o,u) 하나를 반드시 포함하여야 한다.
모음이 3개 혹은 자음이 3개 연속으로 오면 안 된다.
같은 글자가 연속적으로 두번 오면 안되나, ee 와 oo는 허용한다.
이 규칙은 완벽하지 않다;우리에게 친숙하거나 발음이 쉬운 단어 중에서도 품질이 낮게 평가되는 경우가 많이 있다.

입력

입력은 여러개의 테스트 케이스로 이루어져 있다.

각 테스트 케이스는 한 줄로 이루어져 있으며, 각 줄에 테스트할 패스워드가 주어진다.

마지막 테스트 케이스는 end이며, 패스워드는 한글자 이상 20글자 이하의 문자열이다. 또한 패스워드는 대문자를 포함하지 않는다.

출력

각 테스트 케이스를 '예제 출력'의 형태에 기반하여 품질을 평가하여라.

예제 입력

a
tv
ptoui
bontres
zoggax
wiinq
eep
houctuh
end

예제 출력

<a> is acceptable.
<tv> is not acceptable.
<ptoui> is not acceptable.
<bontres> is not acceptable.
<zoggax> is not acceptable.
<wiinq> is not acceptable.
<eep> is acceptable.
<houctuh> is acceptable.

내가 했던 풀이 방법

  1. vowels 배열을 만들고, 모음을 넣어준다.
  2. 입력받은 비밀번호들을 0부터 length-1까지 반복해준다. (length-1까지 반복해주는 이유는 마지막 end는 비밀번호가 아닌 끝을 알려주는 단어이므로 무시해주어야 한다.)
  3. isAllow를 true로 두고, 입력받은 문자열을 공백을 제거해준다.
  4. 현재 검사하는 비밀번호가 vowles에 있는 모음을 가지고 한 개라도 포함하고 있는지를 some과 includes를 이용해 검사한다. true가 아닐 경우, isAllow를 false로 바꾼다.
  5. 현재 비밀번호를 처음부터 length-2까지 세 글자씩 확인하면서, 검사하는 단어의 첫 번째가 모음일 경우, 두 번째/세 번째 모두 모음인지, 첫 번째가 자음일 경우, 두 번째/세 번째가 모두 자음인지를 확인한다. 이에 해당할 경우 isAllow를 false로 바꾼다.
  6. 3~5번을 수행한 뒤에 isAllow가 true일 경우, 비밀번호의 0부터 length-1까지 두 글자씩 확인하면서 첫 번째 글자가 e 또는 o가 아니면서, 두 글자가 같을 경우 isAllow를 false로 바꾼다.
  7. 3~6번을 수행한 뒤에 isAllow가 true일 경우 현재 비밀번호는 가능한 비밀번호이고, false일 경우 현재 비밀번호는 불가능한 비밀번호임을 출력해준다.

코드

const fs = require('fs');
let input = fs.readFileSync(0, 'utf-8').toString().trim().split('\n');

const vowels = ['a', 'e', 'i', 'o', 'u'];
let isAllow = true;
for (let i = 0; i < input.length - 1; i++) {
  isAllow = true;
  input[i] = input[i].trim();
  if (input[i].split('').some((char) => vowels.includes(char))) {
    for (let j = 0; j < input[i].length - 2; j++) {
      if (vowels.includes(input[i].charAt(j))) {
        if (vowels.includes(input[i].charAt(j + 1)) && vowels.includes(input[i].charAt(j + 2))) {
          isAllow = false;
        }
      } else {
        if (!vowels.includes(input[i].charAt(j + 1)) && !vowels.includes(input[i].charAt(j + 2))) {
          isAllow = false;
        }
      }
    }
    if (isAllow) {
      for (let j = 0; j < input[i].length - 1; j++) {
        if (input[i].charAt(j) !== 'e' && input[i].charAt(j) !== 'o' && input[i].charAt(j) === input[i].charAt(j + 1)) {
          isAllow = false;
        }
      }
    }
  } else {
    isAllow = false;
  }
  if (isAllow) {
    console.log(`<${input[i]}> is acceptable.`);
  } else {
    console.log(`<${input[i]}> is not acceptable.`);
  }
}

회고

includes에 제대로 된 사용방법을 몰라서 includes를 사용하자고는 했지만, 예시를 확인한 뒤에 풀이가 가능했다. includes와 some/every에 대해서 제대로 공부해본 적이 없는 것 같긴하다. 다음에 includes와 some/every를 정리해보는 시간을 가져야겠다. 실버 5여서 그런지 문제가 어렵거나 시간초과를 걱정하거나 하진 않았는데 그래도 includes를 생각 못 했으면 풀이에 시간이 오래 걸렸을 것 같긴하다.

profile
Frontend🍓

0개의 댓글