1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
|
---
title: 논리 연산자
slug: >-
conflicting/Web/JavaScript/Reference/Operators_13aeb53e31f9cec454ca631cb162449f
tags:
- JavaScript
- Logic
- Not
- Operator
- Reference
- and
- or
- 논리
translation_of: Web/JavaScript/Reference/Operators
translation_of_original: Web/JavaScript/Reference/Operators/Logical_Operators
original_slug: Web/JavaScript/Reference/Operators/논리_연산자(Logical_Operators)
---
<div>{{jsSidebar("Operators")}}</div>
<p>논리 연산자는 보통 {{jsxref("Boolean")}}(논리적) 값과 함께 쓰이며, 불리언 값을 반환합니다. 그런데, <code>&&</code>과 <code>||</code> 연산자는 사실 피연산자 중 하나의 값을 반환합니다. 그러므로 불리언 외의 다른 값과 함께 사용하면 불리언 값이 아닌 것을 반환할 수 있습니다.</p>
<div>{{EmbedInteractiveExample("pages/js/expressions-logicaloperator.html")}}</div>
<h2 id="설명">설명</h2>
<p>다음 표는 논리 연산자의 종류입니다. (<code><em>expr</em></code>은 불리언을 포함해서 아무 자료형이나 가능합니다)</p>
<table class="fullwidth-table">
<tbody>
<tr>
<th>연산자</th>
<th>구문</th>
<th>설명</th>
</tr>
<tr>
<td>논리 AND (<code>&&</code>)</td>
<td><code><em>expr1</em> && <em>expr2</em></code></td>
<td><code>expr1</code>을 <font face="consolas, Liberation Mono, courier, monospace"><span style="background-color: rgba(220, 220, 220, 0.5);">true</span></font>로 변환할 수 있는 경우 <code>expr2</code>을 반환하고, 그렇지 않으면 <code>expr1</code>을 반환합니다.</td>
</tr>
<tr>
<td>논리 OR (<code>||</code>)</td>
<td><code><em>expr1</em> || <em>expr2</em></code></td>
<td>
<p><code>expr1</code>을 <code>true</code>로 변환할 수 있으면 <code>expr1</code>을 반환하고, 그렇지 않으면 <code>expr2</code>를 반환합니다.</p>
</td>
</tr>
<tr>
<td>논리 NOT (<code>!</code>)</td>
<td><code>!<em>expr</em></code></td>
<td>단일 피연산자를 <code>true</code>로 변환할 수 있으면 <code>false</code>를 반환합니다. 그렇지 않으면 <code>true</code>를 반환합니다.</td>
</tr>
</tbody>
</table>
<p>값을 <code>true</code>로 변환하면 값이 {{Glossary("truthy", "참")}}인 것입니다.<br>
값을 <code>false</code>로 변환할 수 있으면 값이 {{Glossary("falsy", "거짓")}}인 것입니다.</p>
<p>거짓으로 변환할 수 있는 표현의 예는 다음과 같습니다.</p>
<ul>
<li><code>null</code></li>
<li><code>NaN</code></li>
<li><code>0</code></li>
<li>빈 문자열 (<code>"",</code> <code>''</code>, <code>``</code>)</li>
<li><code>undefined</code></li>
</ul>
<p><code>&&</code> 연산자와 <code>||</code> 연산자를 불리언 값이 아닌 피연산자와 함께 사용될 수 있지만, 반환 값을 항상 <a href="/ko/docs/Web/JavaScript/Data_structures#Boolean_%ED%83%80%EC%9E%85">불리언 원시값</a>으로 변환할 수 있으므로 불리언 연산자로 생각할 수 있습니다. 반환 값을 직접 불리언으로 바꾸려면 {{jsxref("Boolean")}} 함수나 이중 부정 연산자를 사용하세요.</p>
<h3 id="단락_평가">단락 평가</h3>
<p>논리 표현식을 좌측부터 평가하므로, 아래 규칙에 따라 단락(short-circuit) 평가를 수행합니다.</p>
<ul>
<li><code>(거짓 표현식) && expr</code>은 거짓 표현식으로 단락 평가됩니다.</li>
<li><code>(참 표현식) || expr</code>은 참 표현식으로 단락 평가됩니다.</li>
</ul>
<p>"단락"이란, 위 규칙에서 <code>expr</code>을 평가하지 않는다는 뜻입니다. 따라서 평가 중 발생해야 할 부작용(예: <code>expr</code>이 함수 호출이면 절대 호출하지 않음)도 나타나지 않습니다. 단락 평가가 발생하는 원인은 첫 번째 피연산자를 평가한 순간 이미 연산자의 결과가 정해지기 때문입니다. 다음 예제를 살펴보세요.</p>
<pre>function A(){ console.log('A 호출'); return false; }
function B(){ console.log('B 호출'); return true; }
console.log( A() && B() );
// 함수 호출로 인해 콘솔에 "A 호출" 기록
// 그 후 연산자의 결과값인 "false" 기록
console.log( B() || A() );
// 함수 호출로 인해 콘솔에 "B 호출" 기록
// 그 후 연산자의 결과인 "true" 기록
</pre>
<h3 id="연산자_우선순위">연산자 우선순위</h3>
<p>다음 두 식은 똑같아 보이지만, <code>&&</code> 연산자는 <code>||</code> 이전에 실행되므로 서로 다릅니다. <a href="/ko/docs/Web/JavaScript/Reference/Operators/Operator_Precedence">연산자 우선순위</a>를 참고하세요.</p>
<pre class="brush: js">true || false && false // returns true, because && is executed first
(true || false) && false // returns false, because operator precedence cannot apply</pre>
<h3 id="논리_AND_()"><a name="Logical_AND">논리 AND (<code>&&</code>)</a></h3>
<p>다음은 <code>&&</code>(논리 AND) 연산자의 예제입니다.</p>
<pre class="brush: js">a1 = true && true // t && t returns true
a2 = true && false // t && f returns false
a3 = false && true // f && t returns false
a4 = false && (3 == 4) // f && f returns false
a5 = 'Cat' && 'Dog' // t && t returns "Dog"
a6 = false && 'Cat' // f && t returns false
a7 = 'Cat' && false // t && f returns false
a8 = '' && false // f && f returns ""
a9 = false && '' // f && f returns false</pre>
<h3 id="논리_OR_()"><a name="Logical_OR">논리 OR (<code>||</code>)</a></h3>
<p>다음은 <code>||</code>(논리 OR) 연산자의 예제입니다.</p>
<pre class="brush: js">o1 = true || true // t || t returns true
o2 = false || true // f || t returns true
o3 = true || false // t || f returns true
o4 = false || (3 == 4) // f || f returns false
o5 = 'Cat' || 'Dog' // t || t returns "Cat"
o6 = false || 'Cat' // f || t returns "Cat"
o7 = 'Cat' || false // t || f returns "Cat"
o8 = '' || false // f || f returns false
o9 = false || '' // f || f returns ""
o10 = false || varObject // f || object returns varObject
</pre>
<h3 id="논리_NOT_(!)"><a name="Logical_NOT">논리 NOT (<code>!</code>)</a></h3>
<p>다음은 <code>!</code>(논리 NOT) 연산자의 예제입니다.</p>
<pre class="brush: js">n1 = !true // !t returns false
n2 = !false // !f returns true
n3 = !'' // !f returns true
n4 = !'Cat' // !t returns false
</pre>
<h4 id="이중_NOT_(!!)">이중 NOT (<code>!!</code>)</h4>
<p>NOT 연산자 다수를 연속해서 사용하면 아무 값이나 불리언 원시값으로 강제 변환할 수 있습니다. 변환 결과는 피연산자 값의 "참스러움"이나 "거짓스러움"에 따릅니다. ({{Glossary("truthy", "참")}}과 {{Glossary("falsy", "거짓")}}을 참고하세요)</p>
<p>동일한 변환을 {{jsxref("Boolean")}} 함수로도 수행할 수 있습니다.</p>
<pre class="brush: js">n1 = !!true // !!truthy returns true
n2 = !!{} // !!truthy returns true: any object is truthy...
n3 = !!(new Boolean(false)) // ...even Boolean objects with a false .valueOf()!
n4 = !!false // !!falsy returns false
n5 = !!"" // !!falsy returns false
n6 = !!Boolean(false) // !!falsy returns false
</pre>
<h3 id="불리언_변환_규칙">불리언 변환 규칙</h3>
<h4 id="AND에서_OR로_변환">AND에서 OR로 변환</h4>
<p>불리언 계산에서, 다음 두 코드는 항상 같습니다.</p>
<pre class="brush: js">bCondition1 && bCondition2
</pre>
<pre class="brush: js">!(!bCondition1 || !bCondition2)</pre>
<h4 id="OR에서_AND로_변환">OR에서 AND로 변환</h4>
<p>불리언 계산에서, 다음 두 코드는 항상 같습니다.</p>
<pre class="brush: js">bCondition1 || bCondition2
</pre>
<pre class="brush: js">!(!bCondition1 && !bCondition2)</pre>
<h4 id="NOT_간_변환">NOT 간 변환</h4>
<p>불리언 계산에서, 다음 두 코드는 항상 같습니다.</p>
<pre class="brush: js">!!bCondition
</pre>
<pre class="brush: js">bCondition</pre>
<h3 id="중첩_괄호_제거">중첩 괄호 제거</h3>
<p>논리 표현식은 항상 왼쪽에서 오른쪽으로 평가되므로, 몇 가지 규칙을 따르면 복잡한 표현식에서 괄호를 제거할 수 있습니다.</p>
<h4 id="중첩_AND_제거">중첩 AND 제거</h4>
<p>불리언의 합성 계산에서, 다음 두 코드는 항상 같습니다.</p>
<pre class="brush: js">bCondition1 || (bCondition2 && bCondition3)
</pre>
<pre class="brush: js">bCondition1 || bCondition2 && bCondition3</pre>
<h4 id="중첩_OR_제거">중첩 OR 제거</h4>
<p>불리언의 합성 계산에서, 다음 두 코드는 항상 같습니다.</p>
<pre class="brush: js">bCondition1 && (bCondition2 || bCondition3)
</pre>
<pre class="brush: js">!(!bCondition1 || !bCondition2 && !bCondition3)</pre>
<h2 id="명세">명세</h2>
<table class="standard-table">
<tbody>
<tr>
<th scope="col">Specification</th>
<th scope="col">Status</th>
<th scope="col">Comment</th>
</tr>
<tr>
<td>{{SpecName('ES1')}}</td>
<td>{{Spec2('ES1')}}</td>
<td>Initial definition.</td>
</tr>
<tr>
<td>{{SpecName('ES5.1', '#sec-11.11')}}</td>
<td>{{Spec2('ES5.1')}}</td>
<td>Defined in several sections of the specification: <a href="http://www.ecma-international.org/ecma-262/5.1/#sec-11.4.9">Logical NOT Operator</a>, <a href="http://www.ecma-international.org/ecma-262/5.1/#sec-11.11">Binary Logical Operators</a></td>
</tr>
<tr>
<td>{{SpecName('ES6', '#sec-binary-logical-operators')}}</td>
<td>{{Spec2('ES6')}}</td>
<td>Defined in several sections of the specification: <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-logical-not-operator">Logical NOT Operator</a>, <a href="http://www.ecma-international.org/ecma-262/6.0/#sec-binary-logical-operators">Binary Logical Operators</a></td>
</tr>
<tr>
<td>{{SpecName('ESDraft', '#sec-binary-logical-operators')}}</td>
<td>{{Spec2('ESDraft')}}</td>
<td>Defined in several sections of the specification: <a href="http://tc39.github.io/ecma262/#sec-logical-not-operator">Logical NOT Operator</a>, <a href="http://tc39.github.io/ecma262/#sec-binary-logical-operators">Binary Logical Operators</a></td>
</tr>
</tbody>
</table>
<h2 id="브라우저_호환성">브라우저 호환성</h2>
<p>{{Compat("javascript.operators.logical")}}</p>
<h2 id="같이_보기">같이 보기</h2>
<ul>
<li><a href="/ko/docs/Web/JavaScript/Reference/Operators/Bitwise_Operators">비트 연산자</a></li>
<li>{{jsxref("Boolean")}}</li>
<li>{{Glossary("truthy", "참")}}</li>
<li>{{Glossary("falsy", "거짓")}}</li>
</ul>
|