Frontend πŸ“š/JavaScript

[JS] 데이터 νƒ€μž…, νƒ€μž… λ³€ν™˜, 단좕 평가 etc.

leejaejae 2024. 7. 30. 14:51

1. 데이터 νƒ€μž… 

1) 데이터 νƒ€μž… μ’…λ₯˜

ꡬ뢄 데이터 νƒ€μž… μ„€λͺ…
μ›μ‹œ νƒ€μž… 숫자(number) νƒ€μž… 숫자, μ •μˆ˜μ™€ μ‹€μˆ˜ ꡬ뢄 없이 ν•˜λ‚˜μ˜ 숫자 νƒ€μž…λ§Œ 쑴재
μ›μ‹œ νƒ€μž… λ¬Έμžμ—΄(string) νƒ€μž… λ¬Έμžμ—΄
μ›μ‹œ νƒ€μž… λΆˆλ¦¬μ–Έ(boolean) νƒ€μž… 논리적 μ°Έ(true)와 거짓(false)
μ›μ‹œ νƒ€μž… undefined νƒ€μž… var ν‚€μ›Œλ“œλ‘œ μ„ μ–Έλ˜λŠ” λ³€μˆ˜μ— μ•”λ¬΅μ μœΌλ‘œ ν• λ‹Ήλ˜λŠ” κ°’
μ›μ‹œ νƒ€μž… null νƒ€μž… 값이 μ—†λ‹€λŠ” 것을 μ˜λ„μ μœΌλ‘œ λͺ…μ‹œν•  λ•Œ μ‚¬μš©ν•˜λŠ” κ°’
μ›μ‹œ νƒ€μž… μ‹¬λ²Œ(symbol) νƒ€μž… ES6μ—μ„œ μΆ”κ°€λœ 7번째 νƒ€μž…
μ›μ‹œ νƒ€μž… BigInt νƒ€μž… 길이의 μ œμ•½ 없이 μ •μˆ˜λ₯Ό λ‹€λ£° 수 있게 ν•΄μ£ΌλŠ” μˆ«μžν˜•
객체 νƒ€μž…   객체, ν•¨μˆ˜, λ°°μ—΄ λ“±

* μ›μ‹œ κ°’(νƒ€μž…)


2) μ‹¬λ²Œ νƒ€μž…μ΄λž€

  • ES6μ—μ„œ μΆ”κ°€λœ 7번째 νƒ€μž…μœΌλ‘œ, λ³€κ²½ λΆˆκ°€λŠ₯ν•œ μ›μ‹œ νƒ€μž…μ˜ κ°’
  • μ‹¬λ²Œ 값은 λ‹€λ₯Έ κ°’κ³Ό μ€‘λ³΅λ˜μ§€ μ•ŠλŠ” μœ μΌλ¬΄μ΄ν•œ κ°’μž„. λ”°λΌμ„œ 주둜 아름이 μΆ©λŒν•œ μœ„ν—˜μ΄ μ—†λŠ” κ°ν…Œμ˜ μœ μΌν•œ ν”„λ‘œνΌν‹° ν‚€λ₯Ό λ§Œλ“€κΈ° μœ„ν•΄ μ‚¬μš©ν•¨
// μœ„, μ•„λž˜, μ™Όμͺ½, 였λ₯Έμͺ½μ„ λ‚˜νƒ€λ‚΄λŠ” μƒμˆ˜λ₯Ό μ •μ˜ν•œλ‹€.
// 쀑볡될 κ°€λŠ₯성이 μ—†λŠ” μ‹¬λ²Œ κ°’μœΌλ‘œ μƒμˆ˜ 값을 μƒμ„±ν•œλ‹€.
const Direction = {
  UP: Symbol('up'),
  DOWN: Symbol('down'),
  LEFT: Symbol('left'),
  RIGHT: Symbol('right'),
};

const myDirection = Direction.UP;

if (myDirection === Direction.UP) {
  console.log('You are going UP.');
}


3) 데이터 νƒ€μž…μ΄ ν•„μš”ν•œ 이유

  • 값을 μ €μž₯ν•  λ•Œ 확보해야 ν•˜λŠ” λ©”λͺ¨λ¦¬ κ³΅κ°„μ˜ 크기λ₯Ό κ²°μ •ν•˜κΈ° μœ„ν•΄
  • 값을 μ°Έμ‘°ν•  λ•Œ ν•œ λ²ˆμ— 읽어 λ“€μ—¬μ•Ό ν•  λ©”λͺ¨λ¦¬ κ³΅κ°„μ˜ 크기λ₯Ό κ²°μ •ν•˜κΈ° μœ„ν•΄
  • λ©”λͺ¨λ¦¬μ—μ„œ 읽어 듀인 2μ§„μˆ˜λ₯Ό μ–΄λ–»κ²Œ 해석할지 κ²°μ •ν•˜κΈ° μœ„ν•΄

 

2. 정적 타이핑 vs. 동적 타이핑

1) 정적 νƒ€μ΄ν•‘μ΄λž€

  • Cλ‚˜ μžλ°” 같은 정적 νƒ€μž… μ–Έμ–΄λŠ” λ³€μˆ˜λ₯Ό μ„ μ–Έν•  λ•Œ λ³€μˆ˜μ— ν• λ‹Ήν•  수 μžˆλŠ” κ°’μ˜ μ’…λ₯˜, 즉 데이터 νƒ€μž…μ„ 사전에 μ„ μ–Έν•΄μ•Ό 함.(이λ₯Ό λͺ…μ‹œμ  νƒ€μž… 선언이라고 함)
  • λ‹€μŒμ€ Cμ—μ„œ μ •μˆ˜ νƒ€μž…μ˜ λ³€μˆ˜λ₯Ό μ„ μ–Έν•˜λŠ” μ˜ˆμ‹œμž„ ↓
// c λ³€μˆ˜μ—λŠ” 1λ°”μ΄νŠΈ μ •μˆ˜ νƒ€μž…μ˜ κ°’(-128 ~ 127)λ§Œμ„ ν• λ‹Ήν•  수 μžˆλ‹€.
char c;

// num λ³€μˆ˜μ—λŠ” 4λ°”μ΄νŠΈ μ •μˆ˜ νƒ€μž…μ˜ κ°’(-2,124,483,648 ~ 2,124,483,647)λ§Œμ„ ν• λ‹Ήν•  수 μžˆλ‹€.
int num;
  • 정적 νƒ€μž… μ–Έμ–΄λŠ” λ³€μˆ˜μ˜ νƒ€μž…μ„ λ³€κ²½ν•  수 μ—†μœΌλ©°, λ³€μˆ˜μ— μ„ μ–Έν•œ νƒ€μž…μ— λ§žλŠ” κ°’λ§Œ ν• λ‹Ήν•  수 있음.
  • 정적 νƒ€μž… μ–Έμ–΄λŠ” 컴파일 μ‹œμ μ—μ„œ νƒ€μž… 체크λ₯Ό μˆ˜ν–‰ν•¨ (λ§Œμ•½, νƒ€μž… 체크λ₯Ό ν†΅κ³Όν•˜μ§€ λͺ»ν–ˆλ‹€λ©΄ μ—λŸ¬λ₯Ό λ°œμƒμ‹œν‚€κ³  ν”„λ‘œκ·Έλž¨μ˜ μ‹€ν–‰ 자체λ₯Ό λ§‰μŒ)
  • λŒ€ν‘œμ μΈ 정적 νƒ€μž… μ–Έμ–΄λ‘œλŠ” C, C++, μžλ°”, μ½”ν‹€λ¦°, κ³ , 러슀트 등이 있음

2) 동적 νƒ€μ΄ν•‘μ΄λž€

  • μžλ°” μŠ€ν¬λ¦½νŠΈλŠ” 정적 νƒ€μž… 언어와 λ‹€λ₯΄κ²Œ λ³€μˆ˜λ₯Όμ„ μ–Έν•  λ•Œ νƒ€μž…μ„ μ„ μ–Έν•˜μ§€ μ•Šκ³  var, let, const ν‚€μ›Œλ“œλ₯Ό μ‚¬μš©ν•΄ λ³€μˆ˜λ₯Ό 선언함
var foo;
console.log(typeof foo); // undefined

foo = 3;
console.log(typeof foo); // number

foo = null;
console.log(typeof foo); // object

foo = Symbol(); // μ‹¬λ²Œ
console.log(typeof foo); // symbol

foo = {}; // 객체
console.log(typeof foo); // object

foo = []; // λ°°μ—΄
console.log(typeof foo); // object

foo = function () {}; // ν•¨μˆ˜
console.log(typeof foo); // function
  • μžλ°”μŠ€ν¬λ¦½νŠΈμ˜ λ³€μˆ˜λŠ” 선언이 μ•„λ‹Œ 할당에 μ˜ν•΄ νƒ€μž…μ΄ κ²°μ •(νƒ€μž… μΆ”λ‘ )됨
  • λ˜ν•œ μž¬ν• λ‹Ήμ— μ˜ν•΄ λ³€μˆ˜μ˜ νƒ€μž…μ€ μ–Έμ œλ“ μ§€ λ™μ μœΌλ‘œ λ³€ν•  수 있음(=동적 타이핑)
  • λŒ€ν‘œμ μΈ 동적 νƒ€μž… μ–Έμ–΄λ‘œλŠ” μžλ°”μŠ€ν¬λ¦½νŠΈ, 파이썬, PHP 등이 있음

 

3. νƒ€μž… λ³€ν™˜

1) λͺ…μ‹œμ  νƒ€μž… λ³€ν™˜

  • μžλ°”μŠ€ν¬λ¦½νŠΈμ˜ λͺ¨λ“  값은 νƒ€μž…μ΄ 있음. κ°’μ˜ νƒ€μž…μ€ 개발자의 μ˜λ„μ— 따라 λ‹€λ₯Έ νƒ€μž…μœΌλ‘œ λ³€ν™˜ν•  수 μžˆλŠ”λ°
  • κ°œλ°œμžκ°€ μ˜λ„μ μœΌλ‘œ κ°’μ˜ νƒ€μž…μ„ λ³€ν™˜ν•˜λŠ” 것을 λͺ…μ‹œμ  νƒ€μž… λ³€ν™˜ λ˜λŠ” νƒ€μž… μΊμŠ€νŒ…μ΄λΌκ³  함
var x = 10;

// 숫자λ₯Ό λ¬Έμžμ—΄λ‘œ νƒ€μž… μΊμŠ€νŒ…ν•œλ‹€.
var str = x.toString();
console.log(typeof str, str); // string 10

// x λ³€μˆ˜μ˜ 값이 λ³€κ²½λœ 것은 μ•„λ‹ˆλ‹€.
console.log(typeof x, x); // number 10

 

2) λͺ…μ‹œμ  νƒ€μž… λ³€ν™˜μ˜ 예

β‘  λ¬Έμžμ—΄μ΄ μ•„λ‹Œ κ°’ → λ¬Έμžμ—΄
- String μƒμ„±μž ν•¨μˆ˜λ₯Ό new μ—°μ‚°μž 없이 ν˜ΈμΆœν•˜λŠ” 법
- Object.prototype.toString λ©”μ„œλ“œλ₯Ό μ‚¬μš©ν•˜λŠ” 법
- λ¬Έμžμ—΄ μ—°κ²° μ—°μ‚°μžλ₯Ό μ΄μš©ν•˜λŠ” 법

// 1. String μƒμ„±μž ν•¨μˆ˜λ₯Ό new μ—°μ‚°μž 없이 ν˜ΈμΆœν•˜λŠ” 방법
String(1); // -> "1"

// 2. Object.prototype.toString λ©”μ„œλ“œλ₯Ό μ‚¬μš©ν•˜λŠ” 방법
(1).toString(); // -> "1"

// 3. λ¬Έμžμ—΄ μ—°κ²° μ—°μ‚°μžλ₯Ό μ΄μš©ν•˜λŠ” 방법
1 + ''; // -> "1"


β‘‘ 숫자 μ•„λ‹Œ κ°’ → 숫자

- Number μƒμ„±μž ν•¨μˆ˜λ₯Ό new μ—°μ‚°μž 없이 ν˜ΈμΆœν•˜λŠ” 방법
- parseInt, parseFloat ν•¨μˆ˜λ₯Ό μ‚¬μš©ν•˜λŠ” 방법(λ¬Έμžμ—΄λ§Œ λ³€ν™˜ κ°€λŠ₯)
- `+` 단항 μ‚°μˆ  μ—°μ‚°μžλ₯Ό μ΄μš©ν•˜λŠ” 방법
- `*` μ‚°μˆ  μ—°μ‚°μžλ₯Ό μ΄μš©ν•˜λŠ” 방법

// 1. Number μƒμ„±μž ν•¨μˆ˜λ₯Ό new μ—°μ‚°μž 없이 ν˜ΈμΆœν•˜λŠ” 방법
Number('0'); // -> 0

// 2. parseInt, parseFloat ν•¨μˆ˜λ₯Ό μ‚¬μš©ν•˜λŠ” 방법(λ¬Έμžμ—΄λ§Œ λ³€ν™˜ κ°€λŠ₯)
parseInt('0'); // -> 0

// 3. + 단항 μ‚°μˆ  μ—°μ‚°μžλ₯Ό μ΄μš©ν•˜λŠ” 방법
+'0'; // -> 0

// 4. * μ‚°μˆ  μ—°μ‚°μžλ₯Ό μ΄μš©ν•˜λŠ” 방법
'0' * 1; // -> 0


β‘’ λΆˆλ¦¬μ–Έ νƒ€μž… μ•„λ‹Œ κ°’ → λΆˆλ¦¬μ–Έ νƒ€μž…
- Boolean μƒμ„±μž ν•¨μˆ˜λ₯Ό new μ—°μ‚°μž 없이 ν˜ΈμΆœν•˜λŠ” 방법
- ! λΆ€μ • 논리 μ—°μ‚°μžλ₯Ό 두 번 μ‚¬μš©ν•˜λŠ” 방법

// 1. Boolean μƒμ„±μž ν•¨μˆ˜λ₯Ό new μ—°μ‚°μž 없이 ν˜ΈμΆœν•˜λŠ” 방법
// λ¬Έμžμ—΄ νƒ€μž… => λΆˆλ¦¬μ–Έ νƒ€μž…
Boolean('x'); // -> true
Boolean(''); // -> false
Boolean('false'); // -> true
// 숫자 νƒ€μž… => λΆˆλ¦¬μ–Έ νƒ€μž…
Boolean(0); // -> false
Boolean(1); // -> true
Boolean(NaN); // -> false
Boolean(Infinity); // -> true
// null νƒ€μž… => λΆˆλ¦¬μ–Έ νƒ€μž…
Boolean(null); // -> false
// undefined νƒ€μž… => λΆˆλ¦¬μ–Έ νƒ€μž…
Boolean(undefined); // -> false
// 객체 νƒ€μž… => λΆˆλ¦¬μ–Έ νƒ€μž…
Boolean({}); // -> true
Boolean([]); // -> true

// 2. ! λΆ€μ • 논리 μ—°μ‚°μžλ₯Ό λ‘λ²ˆ μ‚¬μš©ν•˜λŠ” 방법
// λ¬Έμžμ—΄ νƒ€μž… => λΆˆλ¦¬μ–Έ νƒ€μž…
!!'x'; // -> true
!!''; // -> false
!!'false'; // -> true
// 숫자 νƒ€μž… => λΆˆλ¦¬μ–Έ νƒ€μž…
!!0; // -> false
!!1; // -> true
!!NaN; // -> false
!!Infinity; // -> true
// null νƒ€μž… => λΆˆλ¦¬μ–Έ νƒ€μž…
!!null; // -> false
// undefined νƒ€μž… => λΆˆλ¦¬μ–Έ νƒ€μž…
!!undefined; // -> false
// 객체 νƒ€μž… => λΆˆλ¦¬μ–Έ νƒ€μž…
!!{}; // -> true
!![]; // -> true

 

3) 암묡적 νƒ€μž… λ³€ν™˜

  • 개발자의 μ˜λ„μ™€λŠ” 상관없이 ν‘œν˜„μ‹μ„ ν‰κ°€ν•˜λŠ” 도쀑에 μžλ°”μŠ€ν¬λ¦½νŠΈ 엔진에 μ˜ν•΄ μ•”λ¬΅μ μœΌλ‘œ νƒ€μž…μ΄ μžλ™ λ³€ν™˜λ˜λŠ” 것
var x = 10;

// λ¬Έμžμ—΄ μ—°κ²° μ—°μ‚°μž ( + )λŠ” 숫자 νƒ€μž… x의 값을 λ°”νƒ•μœΌλ‘œ μƒˆλ‘œμš΄ λ¬Έμžμ—΄μ„ μƒμ„±ν•œλ‹€.
var str = x + '';
console.log(typeof str, str); // string 10

// x λ³€μˆ˜μ˜ 값이 λ³€κ²½λœ 것은 μ•„λ‹ˆλ‹€.
console.log(typeof x, x); // number 10

 

Tips. truthy / falsy ν•œ κ°’

  • μžλ°”μŠ€ν¬λ¦½νŠΈ 엔진은 λΆˆλ¦¬μ–Έ νƒ€μž…μ΄ μ•„λ‹Œ 값을 Truthy κ°’(참으둜 ν‰κ°€λ˜λŠ” κ°’) λ˜λŠ” Falsy κ°’(거직으둜 ν‰κ°€λ˜λŠ” κ°’)으둜 ꡬ뢄함
  • 즉, μ œμ–΄λ¬Έμ˜ 쑰건식과 같이 λΆˆλ¦¬μ–Έ κ°’μœΌλ‘œ ν‰κ°€λ˜μ–΄μ•Ό ν•  λ¬Έλ§₯μ—μ„œ Truthy 값은 true둜, Falsy 값은 false둜 암묡적 νƒ€μž… λ³€ν™˜λ¨
// false둜 ν‰κ°€λ˜λŠ” Falsy κ°’
false
undefined
null
0, -0
NaN
' '(빈 λ¬Έμžμ—΄)

// Falsy 값에 ! μ—°μ‚°μžλ₯Ό 뢙이면, λͺ¨λ‘ Truthy κ°’μœΌλ‘œ ν‰κ°€λ˜μ–΄ μ‹€ν–‰ κ°€λŠ₯함
// μ•„λž˜μ˜ 쑰건문은 λͺ¨λ‘ μ½”λ“œ 블둝을 μ‹€ν–‰ν•œ
if (!false) console.log(false + ' is falsy value');
if (!undefined) console.log(undefined + ' is falsy value');
if (!null) console.log(null + ' is falsy value');
if (!0) console.log(0 + ' is falsy value');
if (!NaN) console.log(NaN + ' is falsy value');
if (!'') console.log('' + ' is falsy value');