[딥다이브 스터디] 2주차 (1)

deli-ght·2022년 4월 11일
2

deepdive study

목록 보기
3/7
post-thumbnail

8. 제어문

조건에 따라 코드 블록을 실행(조건문)하거나 반복실행(반복문)할 때 사용

코드의 실행 흐름을 인위적으로 제어할 수 있기 때문에 가독성을 해칠 수 있다는 단점이 있음.
이를 보완하기 위해 고차함수를 이용한 함수형 프로그래밍 기법에서 제어문의 사용을 억제하여 복잡성을 해결

8.1 블록문 (하나의 실행단위)

0개 이상의 문을 중괄호로 묶은 것으로 코드 블록, 또는 블록이라고 부름

자체 종결성을 갖기 때문에 별도로 세미콜론을 붙이지 않아도 됨.

8.2 조건문

주어진 조건식의 평가 결과에 따라 코드 블록의 실행을 결정.

  • 조건식 : = 불리언 값으로 평가될 수 있는 표현식

8.2.1 if...else문

주어진 조건식의 평가 결과에 따라 실행할 블록을 결정 - true : if문 , false : else문

if (조건식1){
    //조건식1이 참이면 이 코드 블록 실행
    //조건식1의 결과값이 불리언 값이 아니더라도 
    //암묵적으로 불리언 타입으로 타입 변환이 이뤄짐
}else if (조건식2){
    //조건식 1이 참이 아니고 
    //조건식2이 참이면 이 코드 블록 실행
    //여러 else if 사용 가능
}else {
    //조건식들이 모두 거짓인 경우
    //이 블록문 실행
}

대부분의 조건문은 삼항 조건 연산자로 변경 가능
삼항 조건 연산자는 값으로 평가되는 표현식을 만들기 때문에 변수에 할당할 수 있다는 차이점이 있음

let even = num === 0 ? '0' : 
           num % 2 === 0 ? 'even' : 'odd'

if...else in JSX
stackoverflow

8.2.2 switch 문

주어진 표현식을 평가하여 그 값과 일치하는 표현식을 가진 case문으로 실행 흐름을 옮김
논리적 참,거짓보다 다양한 상황에 따라 실행할 코드 블럭을 결정할 때 사용

case문은 상황을 의미하는 표현식을 지정하고 콜론으로 마친 뒤, 실행할 문들을 위치시킨다.

일치하는 case문이 없다면 실행 순서는 default문으로 이동. default문은 선택사항

switch(표현식){
    case 표현식1:
        // 표현식 == 표현식 1 -> 실행될 문
        break;
    case 표현식2:
        // 표현식 == 표현식 2 -> 실행될 문
        break;
    default:
        // 일치하는 표현식이 없는 경우 실행
}

break문을 작성하지 않는 경우, 폴스루 발생

  • 폴스루(fall through) : 표현식의 결과가 일치하는 case문이 있었음에도 switch문을 탈출하지 않고 이후 모든 case문과 default문을 실행하는 경우

여러개의 case문을 하나의 조건으로 이용하는 경우 폴스루가 유용하게 사용되기도 함

swich(num){
    case 1: case 3: case 5: case 7: case 9:
        numType = 'odd';
        break;
    default:
        numType = 'even';
        break;
}

8.3 반복문

조건식의 평가 결과가 참인 경우 코드 블록을 실행한다. 그 후 조건식을 다시 평가해 거짓일 때까지 반복 실행한다.

8.3.1 for문

for(1.변수 선언문 또는 할당문; 2. 조건식; 4. 증감식){
    3. 조건식이 참인 경우 반복 실행될 문
    // 이후 2,3,4 반복
}

변수 선언문 또는 할당문에서 var를 사용하는 경우 전역으로 선언되기 때문에 가급적이면 let을 사용하는 것을 권장

8.3.2 while문

for문은 반복 횟수가 명확할 때 주로 사용
while문은 반복 횟수가 불명확할 때 주로 사용

while(조건문){
    //조건문이 항상 참인 경우 무한 루프 발행
    //이런 경우엔 탈출 조건을 만들고 break문으로 탈출
    //if(탈출 조건) break;
}

8.3.3 do...while문

코드 블록을 먼저 실행하고 조건식을 평가하기 때문에 무조건 한 번 이상 코드 블록 실행

8.4 break문

레이블문, 반복문 또는 switch문의 코드 블록을 탈출
이외에 break 사용시 Syntaxerror 발생

레이블문 : 식별자가 붙은 문

fruit : console.log("apple")

  • 프로그램의 실행 순서를 제어하는데 사용
  • switch문의 case문과 default문도 레이블문
  • 중첩된 for문 내부의 for문에서 외부 for문을 탈출하기 위해 레이블문 사용
    outer : for(var i = 0; i<3 ; i++){
        inner : for(var j=0; j<3; j++){
            if(i+j === 3) break outer; 
        }
    }

8.5 continue문

반복문의 코드 블록 실행을 현 지점에서 중단하고 다음 반복으로 넘어감

9. 타입 변환과 단축 평가

9.1 타입 변환이란?

자바스크립트의 모든 값은 타입이 존재
타입은 개발자의 의도에 따라 다른 타입으로 변환이 가능하며 이런 경우
= 명시적 타입 변환 또는 타입 캐스팅

이와 반대로 의도와 관계없이 자바스크립트 엔진에 의해 암묵적으로 타입이 변환되는 경우
= 암묵적 타입 변환 또는 타입 강제 변환

타입 변환은 기존 원시 값을 직접 변경하는 것은 아님(원시값은 변경 불가능한 값)
타입 변환은 기본 원시값을 사용해 다른 타입의 새로운 원시 값을 생성하는 것
암묵적 타입 변환은 새로운 원시 값을 한 번 사용하고 버림

가장 중요한 건 예측 가능한 코드이어야 한다는 것

9.2 암묵적 타입 변환

표현식을 평가할 때 코드의 문맥에 부합하지 않는 다양한 상황이 발생할 수 있음.

// 피연산자가 모두 문자열 타입
'10' + 2 // '102'

// 피연산자가 모두 숫자 타입
5 * '10' // 50

// 피연산자 혹은 표현식이 불리언 타입
!0 // true
if(1){} //1은 true로 형변환

9.2.1 문자열 타입으로 변환

자바스크립트 엔진은 문자열 연결 연산자 표현식을 평가하기 위해 문자열 연결 연산자의 피연산자 중 문자열 타입이 아닌 피연산자를 문자열 타입으로 암묵적 타입 변환

  • 숫자 + 문자열 = 문자열
  • 불리언 + 문자열 = 문자열('true', 'false')
  • null + 문자열 = 문자열
  • undefined + 문자열 = 문자열
  • Symbol타입 + 문자열 = TypeError
  • 객체 타입 + 문자열 = 문자열

9.2.2 숫자 타입으로 변환

산술 연산자의 경우, 숫자값을 만드는 역할을 하기 때문에 문맥상 숫자 타입이 와야함
(+ 산술 연산자는 단항 연산자인 경우만 ex) +'0' -> 0)

따라서 산술 연산자의 피연산자들은 숫자 타입으로 타입 변환이 됨.
숫자 타입으로 변경할 수 없는 피연산자인 경우 NaN을 리턴

비교 연산자 역시 불리언 값을 리턴하기 위해선 두 피연산자를 비교해야하므로 피연산자는 숫자 타입이어야 함.

  • +문자열(숫자) = 숫자
  • +문자열(문자) = NaN
  • +불리언 = true -> 1 , false -> 0
  • +null = 0
  • +undefined = NaN
  • +Symbol() = TypeError
  • +객체 = NaN
    • 예외) 빈 문자열('')과 빈 배열([])은 0으로 치환

9.2.3 불리언 타입으로 변환

제어문 또는 조건식은 불리언 값으로 평가되어야 하는 표현식

자바스트립트 엔진은 불리언타입이 아닌 값을 Truthy값 또는 Falsy값으로 구분

Falsy값

  • false
  • undefined
  • null
  • 0, -0
  • NaN
  • ''(빈 문자열)

9.3 명시적 타입 변환

9.3.1 문자열 타입으로 변한

  1. String 생성자 함수를 new 연산자 없이 호출하는 방법
    • String('Infinity') -> "Infinity"
  2. Object.prototype.toString 메서드를 사용하는 방법
    • (Infinity).toString() -> "Infinity"
  3. 문자열 연결 연산자를 이용하는 방법
    • Infinity + '' -> "Infinity"

9.3.2 숫자 타입으로 변환

  1. Number 생성자 함수를 new 연산자 없이 호출하는 방법
    • Number('0') -> 0
  2. parseInt, parseFloat 함수를 사용하는 방법 (문자열만 숫자 타입으로 변환 가능)
    • parseInt('0') -> 0
  3. + 단항 산술 연산자를 이용하는 방법
    • +'0' -> 0
  4. * 산술 연산자를 이용하는 방법
    • 0 * 1 -> 0

9.3.3 불리언 타입으로 변환

  1. Boolean 생성자 함수를 new 연산자 없이 호출하는 방법
    • Boolean('x') -> true
  2. ! 부정 논리 연산자를 두번 사용하는 방법
    • !!{} -> true
    • !![] -> true

9.4 단축 평가

9.4.1 논리 연산자를 사용한 단축 평가

논리합(||) 또는 논리곱(&&) 연산자 표현식은 언제나 2개의 피연산자 중 어느 한쪽으로 평가됨
이 때 논리 연산의 결과를 결정하는 피연산자를 타입 변환하지 않고 그대로 반환 = 단축 평가
표현식을 평가하는 도중에 평가 결과가 확정된 경우 나머지 평가 과정을 생략하는 것

단축 평가 표현식평가 결과
true \|\| anythingtrue
false \|\| anythinganything
true && anythinganything
false && anythingfalse

단축 평가가 유용한 상황

  • 객체를 가리키기를 기대하는 변수가 null 또는 undefined가 아닌지 확인하고 프로퍼티를 참조할 때
    let value = item && item.value
  • 함수 매개변수에 기본값을 설정할 때
function func1 (arg) {
    arg = arg || '' // 해당 값이 undefined인 경우 기본 값 설정
}

9.4.2 옵셔널 체이닝 연산자 (?.)

좌항의 피연산자가null 또는 undefined인 경우 undefined를 반환
그렇지 않는 경우 프로퍼티 참조를 이어감

&& 로 연산하는 방법도 있지만 0이나 ''는 비어있는 값임에도 객체로 평가되는 경우가 있기때문에 별도로 체크하는 과정이 필요함

따라서 정확성을 위해 객체를 가리키기를 기대하는 변수가 null 또는 undefined가 아닌지 확인하고 프로퍼티를 참조할 때 옵셔널 체이닝을 이용하는 것을 권장

9.4.3 null 병합 연산자

좌항의 피연산자가 null 또는 undefined인 경우 우항의 연산자를 반환
그렇지 않으면 피연산자를 반환
변수에 기본값을 설정할 때 유용

논리연산자의 경우 모든 falsy 값을 걸러내기 때문에 의도적으로 falsy값을 넣는 경우 (0,'' 등) 예기치 못한 동작이 발생할 수 있음.

profile
PRE-FE에서 PRO-FE로🚀🪐!

2개의 댓글

comment-user-thumbnail
2022년 4월 11일

굉장히 잘 정리해주셨네요 .. 감사합니다 !

1개의 답글