함수에 인자를 전달하는 두 가지 방식이 있다.
- call by value
- call by reference
Call by Value
기본형 데이터(Number, String, Boolean, null, undefined, Symbol)를 함수에 인자로 전달할 때 사용된다.
이 방식에서는 변수의 실제 값을 복사하여 함수의 매개변수로 전달한다.
따라서, 함수 내부에서 매개변수의 값을 변경해도 외부 변수에는 영향을 미치지 않는다. (값을 변경해도 원본 값은 변경되지 않는다.)
= 값의 불변성(Immutability)을 유지하는 데에 용이하다.
function changeValue(value) {
value = 10;
}
var x = 5;
changeValue(x);
console.log(x); // 5, x의 값은 변하지 않는다.
위 예시에서 x의 값은 changeValue 함수 내에서 변경되었지만, 원래의 x 값에서는 영향을 미치지 않는다.
- 장점 : 복사하여 처리하기 때문에 안전하다. 원래의 값이 보존된다.
- 단점 : 복사를 하기 때문에 메모리 사용량이 늘어난다.
Call by Reference
참조형 데이터(Object, Array, Function)를 함수에 인자로 전달할 때 사용된다.
이 방식에서는 객체의 참조(메모리 주소)가 함수의 매개변수로 전달된다.
따라서, 함수 내부에서 객체를 변경하면, 그 변경사항이 원본 객체에도 반영된다.
이는 인자로 전달되는 값이 변수의 주소이므로, 함수 내에서 변수의 값을 변경하면 해당 주소에 저장된 값이 변경되기 때문이다.
function changeProperty(obj) {
obj.prop = 10;
}
var myObj = {prop: 5};
changeProperty(myObj);
console.log(myObj.prop); // 10, myObj의 prop 값이 변경되었다.
위 예시에서 myObj 객체는 changeProperty 함수를 통해 변경되었고, 이 변경사항은 원본 객체인 myObj에도 반영되었다.
- 장점 : 복사하지 않고 직접 참조를 하기 때문에 빠르다.
- 단점 : 직접 참조를 하기 때문에 원래 값이 영향을 받는다. (리스크)
Call by Reference의 단점 보완? (불변성 문제)
Call by Reference는 참조 타입을 전달하는 방식이다.
참조 타입의 경우 객체의 참조 값이 복사되므로, 객체 내부의 값이 변경되면 원본 객체도 함꼐 변경되는 문제가 발생한다.
원본의 불변성을 지키기 위해서는 참조형 데이터를 함수에 전달할 때 원본 데이터를 직접 변경하지 않고,
복사본을 작업하여 원본 데이터를 보호하는 방법을 사용해야 한다.
객체의 경우
1. Object.assign() 사용
- Object.assign() 메서드는 대상 객체에 소스 객체의 속성을 복사하여 대상 객체로 반환한다.
- 첫 번째 인자로 빈 객체를 전달하면, 원본 객체를 복사하여 새 객체를 생성할 수 있다.
function updateObject(obj) {
const newObj = Object.assign({}, obj);
newObj.key = 'newValue';
return newObj;
}
const original = { key: 'value' };
const updated = updateObject(original);
console.log(original); // { key: 'value' }
console.log(updated); // { key: 'newValue' }
2. 스프레드 연산자(...) 사용
- 스프레드 연산자를 사용하여 객체의 속성을 새 객체에 복사할 수 있다.
function updateObject(obj) {
const newObj = { ...obj, key: 'newValue' }; // key 속성을 변경하거나 추가
return newObj;
}
const original = { key: 'value' };
const updated = updateObject(original);
console.log(original); // { key: 'value' }
console.log(updated); // { key: 'newValue' }
배열의 경우
1. slice() 사용
- slice() 메서드는 배열의 일부분 혹은 전체를 얕은 복사본으로 만들어 새 배열 객체로 반환한다.
- 원본 배열은 변경되지 않는다.
function addElement(arr) {
const newArr = arr.slice();
newArr.push('newElement');
return newArr;
}
const original = ['element1', 'element2'];
const updated = addElement(original);
console.log(original); // ['element1', 'element2']
console.log(updated); // ['element1', 'element2', 'newElement']
2. 스프레드 연산자(...) 사용
- 배열에 대해서도 스프레드 연산자를 사용하여 원본 배열을 변경하지 않고 새 배열을 생성할 수 있다.
function addElement(arr) {
const newArr = [...arr, 'newElement']; // 배열 끝에 'newElement' 추가
return newArr;
}
const original = ['element1', 'element2'];
const updated = addElement(original);
console.log(original); // ['element1', 'element2']
console.log(updated); // ['element1', 'element2', 'newElement']
'CS' 카테고리의 다른 글
시스템 아키텍처 / 부하 분산 실습 (HAProxy) (0) | 2024.11.22 |
---|---|
[네트워크] HTTP 프로토콜 / 암호화, 복호화 (2) | 2024.11.22 |
[네트워크] DNS 서버, 포트 포워딩, 웹 서버 nginx (0) | 2024.11.21 |
[네트워크] IP 주소, 서브넷 마스크 / 네트워크 설정 (0) | 2024.11.21 |
[네트워크] 네트워크란? / 네트워크의 분류, 통신 방식 / 네트워크 프로토콜 (0) | 2024.11.20 |