본문 바로가기

[JS] test를 통한 type 개념 익히기 _Koans

[JS] test를 통한 type 개념 익히기 _Koans

Koans는 불교에서 유래된 단어로, 결론을 내리기 전에 이게 왜 맞는지 깊게 고민한다는 의미를 가지고 있다고 한다. 답이 미리 제시되어 있기 때문에 고민 없이 풀면, 큰 어려움 없이 전부 다 풀 수 있지만 그게 왜 정답인지 깊게 고민해 보는 시간을 갖지 않는다면 충분히 성장하기 어려울 것이다. 즉, '왜?' 라는 물음에 대해 꼭 깊은 고찰을 하고 넘어가자는 의미이다.


describe('type에 대해서 학습합니다.', function () {

it("비교연산자 '=='는 두 값의 일치 여부를 느슨하게 검사(loose equality)합니다.", function () {
let actualValue = 1 + 1;
let expectedValue = '2';
expect(actualValue == expectedValue).to.be.true;

/*
여기서 expectedValue가 문자열 '2'인데도 테스트는 통과가 된다.
'=='의 실행 중 타입 변환(type coercion)이 일어나기 때문입니다.
이는 다소 복잡하고, 명확한 규칙이 존재하지 않는다.
느슨한 동치 연산자 '=='의 느슨함을 보여주는 예시가 아래에 있다. (다 통과되는 케이스) 
*/

// expect(0 == false).to.be.true;
// expect('' == false).to.be.true;
// expect([] == false).to.be.true;    //** 주석 1) []는 truthy 값이다. (혼동X)
// expect(![] == false).to.be.true;   //** 주석 1) ![]는 falsy 값이다.
// expect([] == ![]).to.be.true;      //** 주석 1) 코드블럭 밑 주석 1 그림 참조  
// expect([] == '').to.be.true;
// expect([] == 0).to.be.true;
// expect([''] == '').to.be.true;
// expect([''] == 0).to.be.true;
// expect([0] == 0).to.be.true;
});

/*
느슨한 동치 연산(loose equality)는 프로그램의 작동을 예측하기 다소 어렵게 만든다.
반드시 엄격한 동치 연산(strict equality) '==='을 사용하도록 하자.
*/

it("비교연산자 '==='는 두 값의 일치 여부를 엄격하게 검사(strict equality)합니다.", function () {
let actualValue = 1 + 1;
let expectedValue = 2;
expect(actualValue === expectedValue).to.be.true;
// 이제 'FILL_ME_IN'을 대신할 수 있는 건 number 타입의 2뿐이다. (문자열 '2'는 통과X)

});

it('expect의 전달인자로 들어간 표현식의 평가(evaluation) 결과를 예측해 봅니다.', function () {
expect(1 + '1').to.equal('11');
});

it('expect의 전달인자로 들어간 표현식의 평가(evaluation) 결과를 예측해 봅니다.', function () {
expect(123 - '1').to.equal(122);                 //** + 연산을 제외하고는 문자열을 숫자로 취급
});

it('expect의 전달인자로 들어간 표현식의 평가(evaluation) 결과를 예측해 봅니다.', function () {
expect(1 + true).to.equal(2);                    // 연산에서의 true의 값은 1이다.
});

it('expect의 전달인자로 들어간 표현식의 평가(evaluation) 결과를 예측해 봅니다.', function () {
expect('1' + true).to.equal('1true');
});

});​

주석 1

== 와 === 를 한눈에 비교할 수 있는 표. 앞으로 내 사전에 '동치 연산자'는 === 밖에 없다!


[]와 ![]은 같다

[] == ![] 라고???

한동안 벙 쪘다..... 그도 그럴듯이 자바스크립트에는 다소 이해하기 힘든 부분들이 존재하며 아래처럼 자바스크립트의 별난(quirky) 부분들을 따로 모아둔 저장소도 있다. 
https://github.com/denysdovhan/wtfjs

 

GitHub - denysdovhan/wtfjs: 🤪 A list of funny and tricky JavaScript examples

🤪 A list of funny and tricky JavaScript examples. Contribute to denysdovhan/wtfjs development by creating an account on GitHub.

github.com

역시 위의 링크에 들어가보니 [] == ![] 가 제일 첫 예시로 등장했다.. ㅋㅋㅋ 이유는 다음과 같다. (영어 원본을 보는 것을 추천)

[] == ![]; // -> true

💡 설명:

추상 항등 연산자는 양쪽을 숫자로 변환하여 비교하고, 서로 다른 이유로 양 쪽의 숫자는 0이 된다.

  • ![] : 배열은 truthy 하므로, 오른쪽의 값은 truthy value의 반대 값 즉, false가 된다. (false는 곧 0)
  • [] : 빈 배열은 먼저 boolean이 되지 않고 숫자로 강제 변환되고 빈 배열은 truthy 임에도 불구하고 0으로 강요된다.
[] == ![] // Array, Boolean+Array
0 == ![] // Number, Boolean+Array
0 == false // Number, Boolean
0 == 0 // Number, Number

true

참조 []은 truthy 이지만 true은 아니다.


true는 ![]와 같지 않지만, []와도 같지 않다

true == []; // -> false
true == ![]; // -> false

false == []; // -> true
false == ![]; // -> true

 

💡 설명:

true == []; // -> false
true == ![]; // -> false

// According to the specification

true == []; // -> false

toNumber(true); // -> 1
toNumber([]); // -> 0

1 == 0; // -> false

true == ![]; // -> false

![]; // -> false

true == false; // -> false

false == []; // -> true
false == ![]; // -> true

// According to the specification

false == []; // -> true

toNumber(false); // -> 0
toNumber([]); // -> 0

0 == 0; // -> true

false == ![]; // -> true

![]; // -> false

false == false; // -> true


그냥 그렇구나~ 의 자세를 가지도록 하자. 


 

728x90
⬆︎