[연습문제] 애너그램, 2진수의가장먼1거리




애너그램(해쉬맵)

Anagram이란 두 문자열이 알파벳의 나열 순서는 다르지만 그 구성이 일치하면 두 단어는 아나그램이라고 합니다.
예를 들면 AbaAeCe와 baeeACA는 알파벳 나열 순서는 다르지만 그 구성을 살펴보면 A(2), a(1), b(1), C(1), e(2)로 알파벳과 그 개수가 모두 일치합니다.
즉 어느 한 단어를 재배열하면 상대편 단어가 될 수 있는 것을 아나그램이라 합니다.
길이가 같은 두 개의 단어가 주어지면 두 단어가 아나그램인지 판별하는 프로그램을 작성하세요.
아나그램 판별시 대소문자가 구분됩니다.

(‘AbaAeCe’, ‘baeeACA’) => true
(‘abaCC’, ‘Caaab’) => fase

애너그램 판별: 문자열을 구성하는 각 문자의 갯수가 일치하면 애너그램이다.

처음 짠 코드

function isAnagram(str1, str2) {
  let strArr1 = str1.split('').sort();
  let strArr2 = str2.split('').sort();
  return strArr2.filter((v, i) => {
    return v != strArr1[i];
  }).length
    ? false
    : true;
}

sort를 활용했는데 강사님께서 sort는 사기라고 하셨다.ㅎㅎ
그래서 두번째 버전은 해시를 사용해보자.



함수형 코드

function makeHash(str) {
  return [...str].reduce((acc, cur) => {
    acc[cur] = (acc[cur] || 0) + 1;
    return acc;
  }, {});
}

function isAnagram(str1, str2) {
  if (str1.length !== str2.length) return false;

  const hash1 = makeHash(str1);
  const hash2 = makeHash(str2);

  return Object.keys(hash1).every(v => hash1[v] === hash2[v]);
}

console.log(isAnagram('AbaAeCe', 'baeeACA')); // true
console.log(isAnagram('abaCC', 'Caaab')); // false
console.log(isAnagram('', 'b')); // false

Array 내장 메서드를 활용하여 함수형 프로그래밍으로 수정하였다.
함수형 프로그래밍으로 코드를 짜려면 다음을 기억하자.

  1. 변수 선언 자제 (내장 메서드 변수 활용)
  2. for문 사용 안하기
  3. 상황에 맞는 Array 내장 메서드 활용하기


hash1과 hash2도 return 에 바로 체이닝을 걸 수는 있지만, 그럼 반복할 때마다 해당 과정을 수행하므로 미리 변수에 선언해두었다.


2진수의가장먼1거리

2진수의가장먼1

function solution(n) {
  const stack = [];
  const result = [];
  let cnt = 0;
  [...n.toString(2)].forEach(v => {
    stack.push(v);
    if (v == 0) {
      cnt++;
    } else {
      result.push(cnt);
      cnt = 0;
    }
  });

  return Math.max(...result) + 1;
}

console.log(solution(67108865));