출처: https://javascript.info/function-basics
Functions
javascript.info
함수
자바스크립트에서 함수는 스크립트의 여러 위치에서 비슷한 동작을 반복 수행할 필요가 있을 때 사용함.
예를 들어 방문자가 로그인하거나 로그아웃할 떄 멋진 메시지를 보여줘야 한다면 , 함수를 사용하면 코드 중복 없이 해당 메시지를 여러 번 호출할 수 있음.
함수는 프로그램의 주요 " 빌딩 블록 " 임.
한 번 정의한 함수를 여러 번 호출하여 동일한 동작을 실행할 수 있음.
우리는 이미 alert(message) , prompt(message , default)와 confirm(question)같은 내장 함수의 예를 보았음.
하지만 우리는 직접 함수를 만들수도 있음.
함수 선언
함수를 생성하는 가장 기본적인 방법은 함수 선언문(function declaration)을 사용하는 것
문법은 다음과 같음 :
function showMessage() {
alert( 'Hello everyone!' );
}
먼저 function 키워드를 쓰고
그 다음 함수 이름을 지정하며
괄호 안에는 매개변수 목록(쉼표로 구분됨, 위 예제에서는 비어 있음)이 옴.
마지막으로 중괄호 {...}안에 함수 본문 (코드)이 위치함.
일반적인 형태는 다음과 같음 .
function name(parameter1, parameter2, ... parameterN) {
// 본문(body)
}
정의한 함수는 이름을 통해 호출할 수 있음 예를 들어 :
function showMessage() {
alert( 'Hello everyone!' );
}
showMessage();
showMessage();
위와 같이 showMessage()를 호출하면 함수 내의 코드가 실행되며 , 여기서는 메시지가 두 번 출력됨.
이 예제는 함수의 주요 목적 중 하나인 코드 중복 제거를 잘 보여줌.
메시지나 출력 방식을 변경할 때 한 군데만 수정하면 되기 때문임.
지역 변수 (Local variables)
함수 내부에서 선언된 변수는 해당 함수 내부에서만 유효함.
예시 :
function showMessage() {
let message = "Hello, I'm JavaScript!"; // 지역 변수
alert( message );
}
showMessage(); // "Hello, I'm JavaScript!" 출력
alert( message ); // <-- 오류! message 변수는 함수 내부에서만 유효함
외부 변수 (Outer variables)
함수는 외부에 선언된 변수에도 접근할 수 있음.
예시 :
let userName = 'John';
function showMessage() {
let message = 'Hello, ' + userName;
alert(message);
}
showMessage(); // "Hello, John" 출력
함수는 외부 변수를 완전히 읽을 수 있으며 , 수정할 수도 있음.
예를 들어:
let userName = 'John';
function showMessage() {
userName = "Bob"; // (1) 외부 변수를 변경함
let message = 'Hello, ' + userName;
alert(message);
}
alert( userName ); // 함수 호출 전: "John"
showMessage();
alert( userName ); // 함수 호출 후: "Bob", 함수가 외부 변수의 값을 변경함
주의 : 만약 함수 내부에서 같은 이름의 변수를 다시 선언하면, 해당 함수는 내부의 변수를 우선 사용하고 외부 변수는 무시하게 됨.
예시 :
let userName = 'John';
function showMessage() {
let userName = "Bob"; // 지역 변수 선언
let message = 'Hello, ' + userName; // "Bob" 사용됨
alert(message);
}
showMessage();
alert( userName ); // "John", 외부 변수는 변경되지 않음
전역 변수(Global variables)
함수 외부에서 선언된 변수(예: 위의 외부 변수 username)는 전역 변수라고 하며 , 특별한 경우를 제외하면 모든 함수에서 접근할 수 있음.
그러나 전역 변수의 사용은 최소화하는 것이 좋은 습관임.
최신 코드에서는 전역 변수의 사용을 줄이고 , 대부분의 변수는 함수 내부에 위치함.
다만, 프로젝트 전체의 데이터를 저장할 때 전역 변수가 유용할 수 있음.
매개변수 (Parameters)
함수에 데이터를 전달할 떄 매개변수를 사용함.
아래 예제에서 함수는 두 개의 매개변수 from과 text를 갖음 :
function showMessage(from, text) { // 매개변수: from, text
alert(from + ': ' + text);
}
showMessage('Ann', 'Hello!'); // "Ann: Hello!" 출력
showMessage('Ann', "What's up?"); // "Ann: What's up?" 출력
함수가 호출될 때 전달된 값들은 해당 매개변수에 복사되어 함수 내부에서 사용됨.
또 다른 예제 : 외부 변수 from을 함수에 전달한 후 , 함수 내부에서 매개변수 from의 값을 변경해도 외부 변수는 변경되지 않음.
function showMessage(from, text) {
from = '*' + from + '*'; // 매개변수 from을 예쁘게 변경함
alert( from + ': ' + text );
}
let from = "Ann";
showMessage(from, "Hello"); // 출력: "*Ann*: Hello"
alert( from ); // "Ann", 함수 내부에서 수정한 값은 외부에 영향을 주지 않음
참고 : 함수에 전달되는 값을 인수(argument)라고 부르며 함수 선언 시 나열하는 매개변수 (parameter)와 구분됨.
즉 함수 showmessage 는 두 개의 매개변수를 가지고 선언되고 , 호출될 때 두 개의 인수 , 예를 들어 from 과 "hello"가 전달된다 라고 표현할 수 있음.
함수에 선언된 것은 매개 변수 , 매개 변수의 전달되는 값을 인수라고 함.
기본값(Default values)
함수를 호출할 때 인수가 제공되지 않으면, 해당 매개변수의 값은 undefined가 됨.
예를 들어 앞서 사용한 함수 showMessage(from , text)를 단일 인수로 호출하면 :
showMessage("Ann");
오류가 발생하지 않으며 , 출력은 "Ann: undefined" 됨.
매개변수 text가 전달되지 않았으므로 undefined가 됨.
매개변수에 기본값을 지정할수도 있음. 이는 매개변수 선언 시 = 기호를 사용하여 지정함. :
function showMessage(from, text = "no text given") {
alert( from + ": " + text );
}
showMessage("Ann"); // "Ann: no text given" 출력
만약 인수가 undefined로 전달되더라도 기본값이 사용됨 :
showMessage("Ann", undefined); // "Ann: no text given" 출력
기본값은 복잡한 표현식도 될 수 있으며 , 매개변수가 전달되지 않은 경우에만 평가되어 할당됨.
예:
function showMessage(from, text = anotherFunction()) {
// 인수가 없으면 anotherFunction()이 실행되고 그 결과가 text에 할당됨
}
기본값은 복잡한 표현식도 될 수 있으며, 매개변수가 전달되지 않은 경우에만 평가되어 할당됨.
여기서 text = anotherFunction() 을 이야기함.
기본 매개변수의 평가
자바스크립트에서는 함수가 호출될 때마다 , 해당 매개변수가 전달되지 않으면 기본값이 평가됨.
예를 들어 위 코드에서 text 매개변수가 전달되면 anotherFunction()은 실행되지 않지만 전달되지 않으면 매번 실행이 됨.
이전 버전의 자바스크립트에서 기본값 지정
몇 년 전에는 자바스크립트가 기본 매개변수 문법을 지원하지 않았기 때문에 , 다음과 같이 직접 undefined를 체크하는 방식으로 기본값을 지정했음.
function showMessage(from, text) {
if (text === undefined) {
text = 'no text given';
}
alert( from + ": " + text );
}
여기선 text가 undefined 일 때 즉 아무것도 할당이 되지 않았을 떄를 처리해줌.
또는 OR 연산자(||)를 사용하기도 했음. :
function showMessage(from, text) {
// text가 falsy하면 기본값을 할당함 (빈 문자열 ""도 기본값으로 간주됨)
text = text || 'no text given';
// ...
}
대체 기본 매개변수
경우에 따라 함수 선언 후에 매개변수의 기본값을 설정할 수 도 있음.
function showMessage(text) {
// ...
if (text === undefined) { // 매개변수가 전달되지 않은 경우
text = 'empty message';
}
alert(text);
}
showMessage(); // "empty message" 출력
또는 OR 연산자를 사용할 수 있음:
function showMessage(text) {
// text가 undefined이거나 falsy하면 'empty'로 설정
text = text || 'empty';
// ...
}
모던 자바스크립트 엔진에서는 nullish 병합 연산자 (??)를 지원하므로 0과 같은 falsy 값들을 정상적인 값으로 취급할 때는 더 나은 선택임 :
function showCount(count) {
// count가 undefined 또는 null이면 "unknown" 출력
alert(count ?? "unknown");
}
showCount(0); // 0 출력
showCount(null); // "unknown" 출력
showCount(); // "unknown" 출력
값을 변환하기 (Returning a value)
함수는 실행 결과로 값을 호출한 곳에 반환할 수 있음.
가장 간단한 예로 두 값을 더하는 함수를 들 수 있음 :
function sum(a, b) {
return a + b;
}
let result = sum(1, 2);
alert( result ); // 3 출력
return문을 만나면 함수의 실행은 즉시 종료되고 , 반환된 값은 호출한 코드에 전달됨.
하나의 함수 안에 여러 개의 return 문이 있을 수도 있음. 예를 들어 :
function checkAge(age) {
if (age >= 18) {
return true;
} else {
return confirm('Do you have permission from your parents?');
}
}
let age = prompt('How old are you?', 18);
if ( checkAge(age) ) {
alert( 'Access granted' );
} else {
alert( 'Access denied' );
}
함수 내에서 값 없이 return을 사용하면 , 함수는 즉시 종료되며 undefined를 반환함.
예를 들어 :
function showMovie(age) {
if ( !checkAge(age) ) {
return;
}
alert( "Showing you the movie" );
// ...
}
또한 , 함수에서 반환 값이 없으면 암묵적으로 undefined가 반환됨 :
function doNothing() { /* 아무 작업도 하지 않음 */ }
alert( doNothing() === undefined ); // true
빈 return은 return undefined; 와 동일 :
function doNothing() {
return;
}
alert( doNothing() === undefined ); // true
주의 : 긴 표현식을 여러 줄에 걸쳐 반환하려고 할 떄 , return과 반환값 사이에 줄바꿈을 넣으면 자바스크립트는 자동으로 세미콜론을 추가하여 빈 값을 반환하게 됨.
올바른 예 :
return (
some + long + expression
+ or +
whatever * f(a) + f(b)
);
반드시 반환 값이 return 과 같은 줄에 시작하도록 하거나 , 괄호를 사용
한 함수는 한 가지 동작만 수행하기
함수는 그 이름이 암시하는 작업만 수행해야 하며 , 그 이상의 부수 효과가 없어야 함.
예를 들어 , 두가지 독립적인 작업은 보통 각각 별도의 함수로 분리하는 것이 좋음.
함께 호출되더라도 , 각 작업은 개별 함수로 구현하고 , 필요시 이를 묶는 또 다른 함수를 만들면 됨.
예시 :
getAge 함수는 단순히 나이를 반환하기만 해야 하며 , 동시에 alert를 호출하면 안됨.
createForm 함수는 폼을 생성하고 반환해야 하며 , 문서에 직접 추가하는 등의 부수 효과가 없어야 함.
checkpermission 함수는 단순히 권한을 검사하여 결과를 반환해야 하며 , 그 결과를 화면에 출력하면 안됨.
이러한 규칙은 함수 이름에 내포된 의미를 명확하게 하고 , 팀 내에서 일관된 코딩 스타일을 유지하는데 도움을 줌.
초단기 함수 이름
자주 사용되는 함수의 경우 , jQuery의 $나 Lodash의 _ 와 같이 아주 짧은 이름을 사용하는 경우도 있음.
하지만 이는 예외이며 , 일반적으로 함수 이름은 간결하면서도 설명적이어야 함.
함수는 곧 주석과 같다
함수는 짧고 하나의 동작만 수행해야 함.
만약 하나의 동작이 너무 크다면 , 여러 개의 작은 함수로 나누는 것이 좋음.
함수를 별도로 분리하면 테스트와 디버깅이 쉬어지며 , 함수 자체가 훌륭한 주석 역할을 함.
예를 들어 , n이하의 소수를 출력하는 두가지 버전의 showPrimes(n) 함수가 있다고 함.
첫 번째 버전은 레이블을 사용함 :
function showPrimes(n) {
nextPrime: for (let i = 2; i < n; i++) {
for (let j = 2; j < i; j++) {
if (i % j == 0) continue nextPrime;
}
alert( i ); // 소수 출력
}
}
두번째 버전은 소수 여부를 검사하는 별도의 함수 isprime(n)을 사용함 :
function showPrimes(n) {
for (let i = 2; i < n; i++) {
if (!isPrime(i)) continue;
alert(i); // 소수 출력
}
}
function isPrime(n) {
for (let i = 2; i < n; i++) {
if ( n % i == 0) return false;
}
return true;
}
두번째 버전이 훨씬 이해하기 쉬움. 코드 조각 대신 , 함수 이름 isPrime이 수행하는 작업을 바로 알 수 있기 때문임.
때때로 재사용할 의도가 없더라도 , 코드를 구조화하고 가독성을 높이기 위해 함수를 만드는 것이 좋음.
과제
1.다음 함수는 매개변수 age가 18보다 크면 true를 반환하고 , 그렇지 않으면 확인창(confirm)을 띄워 그 결과를 반환함.
function checkAge(age) {
if (age > 18) {
return true;
} else {
// ...
return confirm('Did parents allow you?');
}
}
아래와 같이 else를 제거한 경우와 동작이 달라질까?
function checkAge(age) {
if (age > 18) {
return true;
}
// ...
return confirm('Did parents allow you?');
}
안 달라진다.
2. 다음 함수는 매개변수 age가 18보다 크면 true를 반환하고 , 그렇지 않으면 확인창 (confirm)을
띄워 그 결과를 반환함.
function checkAge(age) {
if (age > 18) {
return true;
} else {
return confirm('Did parents allow you?');
}
}
이 함수를 if 문 없이 한 줄로 동일한 동작을 하도록 작
짠 코드
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Document</title>
</head>
<body>
<script>
age = prompt("나이 입력","입력")
checkAge()
function checkAge(age){
return age > 18 ? true : confirm('Did parents allow you?')
}
</script>
</body>
</html>
다른 예시
OR (||)을 이용한 방법
function checkAge(age) {
return (age > 18) || confirm('Did parents allow you?');
}
3. 두 숫자 a와 b 중 작은 값을 반환하는 함수 min(a,b)를 작성
짠 코드 :
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Document</title>
</head>
<body>
<script>
a = prompt(" a를 입력","a")
a = Number(a)
b = prompt(" b를 입력","b")
b = Number(b)
result = min(a,b)
alert(result)
function min(a , b){
if(a > b){
return b}
if(a < b){
return a
}
}
</script>
</body>
</html>
4.함수 pow(x,n)을 작성하여 x를 n번 곱한 값을 반환하는 프로그램 만들기
짠 코드
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Document</title>
</head>
<body>
<script>
x = prompt(" x를 입력","x")
x = Number(x)
n = prompt(" n를 입력","n")
n = Number(n)
value = pow(x,n)
alert(value)
function pow(x , n){
let result = x
for(let i = 1; i < n;i++){
result *= x
}
return result
}
</script>
</body>
</html>
'언어' 카테고리의 다른 글
| Arrow functions, the basics (JavaScript) (0) | 2025.03.14 |
|---|---|
| Function expressions (JavaScript) (0) | 2025.03.14 |
| The "switch" statement (JavaScript) (0) | 2025.03.14 |
| Loops: while and for (0) | 2025.03.14 |
| Nullish coalescing operator '??' (JavaScript) (0) | 2025.03.13 |