๋ค์ด๊ฐ๋ฉฐ
์ฝ์ด์๋ฐ์คํฌ๋ฆฝํธ ์ฑ
์ ์ฑํฐ 1. ๋ฐ์ดํฐ ํ์
์ ์ฝ๊ณ ๋ ํ ์ดํดํ ์ ์ ๋ฐํ์ผ๋ก ์ฌ๊ตฌ์ฑํ์ฌ ์ด ๊ธ์ด๋ค.
์ด ์ฑํฐ๋ฅผ ์ฝ์ผ๋ฉด์ ์ ๊ธฐ๋ณธํ ๋ฐ์ดํฐ์ ์ฐธ์กฐํ ๋ฐ์ดํฐ๋ฅผ ์์์ผ ํ๋ ๊ฑด์ง, ๊ทธ๋ฆฌ๊ณ ์ด ์ง์์ ์์์ ๋ ์ด๋ค ๊ฐ์น๋ฅผ ๊ฐ์ ธ๋ค ์ฃผ๋์ง๋ฅผ ๊ณ์ ์๊ธฐํ๋ฉด์ ์ดํดํ๋ ค๊ณ ํ๋ค. ์ฑํฐ๋ฅผ ์ฝ๊ณ ๋ ํ์ ํฐ ๊ฒฐ๋ก ์ ์ด์ผ๊ธฐ ํ์๋ฉด ๊ฒฐ๊ตญ ๋ฉ๋ชจ๋ฆฌ ๊ด๋ฆฌ์ ํจ์จ์ฑ์ ์ํ ๊ฒ์ด๋ค.
๋ฉ๋ชจ๋ฆฌ๋ฅผ ํจ์จ์ ์ผ๋ก ์ด๋ค๋ ๊ฒ์ ๋ฐ์ดํฐ ํ์ ์์๋ ๋ณ์์ ํ ๋น ๋ ๋ฐ์ดํฐ๋ค์ ๋งค๋ฒ ์๋ก ์์ฑ ํ์ง ์๊ณ ๊ฐ์ ๊ฐ์ ๊ฐ์ง๊ณ ์๋ ๋ฐ์ดํฐ ์์ญ(๋ค์ ์ค๋ช ๋ ๊ฒ์ด๋ค) ์ ๋ฉ๋ชจ๋ฆฌ์์ ์ฃผ์๊ฐ์ ์ฐธ์กฐ ํ๋ค๋ ๊ฒ์ด๋ค.(์ฌ์ฌ์ฉ ๊ฐ๋ฅ)
๊ทธ๋ฆฌ๊ณ ๊ธฐ๋ณธํ ๋ฐ์ดํฐ์ ์ฐธ์กฐํ๋ฐ์ดํฐ๋ฅผ ์ฌ์ฉํ๋ ๊ณผ์ ์์ ์ฐ๋ฆฌ๋ ๋งค ์ฐ์ฐ๋ง๋ค ์ด๋ค์ด ์ด๋ป๊ฒ ๋ฉ๋ชจ๋ฆฌ์์ ํ์ฉ๋๊ณ ์๋์ง, ์ด ๋ฐ์ดํฐ๋ค์ด ์ด๋ป๊ฒ ๋ณํ๋์ง ์์ธก ํ ์ ์์ด์ผ ํ๋ค๊ณ ์๊ฐํ๋ค. ๊ทธ ์ด์ ๋ ์ด ๋์ ๋ฐ์ดํฐ๋ฅผ ๋ค๋ฃจ๋ ๋ฐฉ์์ด ๋ค๋ฅธ๋ฐ ํ๋ก๊ทธ๋๋จธ๋ก์ ๋ฐฉ์์ ์๊ณ ์๋ค๋ฉด ์์ฑํ๋ ๋ก์ง์ ์์ธก์ด ๋ ์ฌ์์ง ๊ฒ์ด๋ผ๊ณ ์์ํ๋ค.
๊ฐ์ฒด๋ ๊ฐ๋ณ์ (mutable) ์ด๋ผ๊ณ ํ๋๋ฐ, ๋ด๋ถ ๋์ ์๋ฆฌ๊ฐ ์ด๋ป๊ฒ ๋๋์ง? ๊ทธ๋ฆฌ๊ณ "๊ธฐ๋ณธํ ๋ฐ์ดํฐ๊ฐ ๋ถ๋ณ(immutable)ํ๋ค" ๋ฅผ ๋ฉ๋ชจ๋ฆฌ ๊ด์ ์์ ์ค๋ช ํ ์ ์๋์ง? ์ ๋ํ ๊ถ๊ธ์ฆ์ด ํด์๊ฐ ๋ ์ ์์ ๊ฒ์ด๋ค.
๊ธฐ๋ณธํ ๋ฐ์ดํฐ์ ๋ถ๋ณ์ฑ(immutability) ์ฆ๋ช ํ๊ธฐ
์ ์ : ๊ธฐ๋ณธํ ๋ฐ์ดํฐ๊ฐ ๋ถ๋ณ์ด์ง ๊ธฐ๋ณธํ ๋ฐ์ดํฐ๋ฅผ ๋ด์ ๋ณ์๊ฐ ๋ถ๋ณ์ธ ๊ฒ์ ์๋๋ค.
- ๊ธฐ๋ณธํ ๋ฐ์ดํฐ๋ ์ฑ ์์ ๋งํ๋ ๋ฉ๋ชจ๋ฆฌ๋ฅผ ๋ฐ์ดํฐ ์์ญ๊ณผ ๋ณ์ ์์ญ์ผ๋ก ๊ตฌ๋ถ ํ ๊ฒ์์, ๋ฐ์ดํฐ ์์ญ์ ๋ฉ๋ชจ๋ฆฌ๋ฅผ ์ด์ผ๊ธฐ ํ๋ค.
- ๋ฐ์ดํฐ ์์ญ์ ๋ฉ๋ชจ๋ฆฌ๋ ์ฃผ์์ธ๋ฐ ๊ธฐ๋ณธํ ๋ฐ์ดํฐ ๊ฐ์ ๊ฐ์ง ์ ์๋ ์ฃผ์๋ก ์ดํด ํด๋ ๋ ๊ฒ ๊ฐ๋ค.(์๋ ์ด๋ฏธ์ง์ ํ์&ํ๋์ ๋ฉ๋ชจ๋ฆฌ์ฃผ์ ๋ถ๋ถ ์ฐธ๊ณ )
- ๋ณ์ ์์ญ์ ๋ฐ์ดํฐ๊ฐ ๋ด๊ธด ๋ฐ์ดํฐ ์์ญ์ ๋ฉ๋ชจ๋ฆฌ ์ฃผ์๊ฐ ํ ๋น๋๋ค.
var a = 10;
var b = a;
console.log(b) // 10
b = 0;
console.log(b) // 0
console.log(a) // 10
๋ถ๋ณ์ ์ค๋ช ํ๊ธฐ ์ํด์ b๋ผ๋ ๋ณ์๊ฐ 0์ผ๋ก ์ฌํ ๋น ๋์์ ๋, ๋ฐ์ดํฐ ์์ญ์ 5000๋ฒ์์ ๋ฐ์ดํฐ ๊ฐ์ด 10->0 ์ผ๋ก ๋ณํํ๋๊ฑธ ๊ธฐ๋ํ์ ์๋ ์๊ฒ ์ง๋ง, ๊ทธ๋ ๊ฒ ๋๋ฉด ๋ถ๋ณ์ฑ์ด ์๋๋ค. ๊ทธ ์ด์ ๋ ์ด๋ฏธ 10์ด๋ผ๋ ๊ฐ์ ๊ฐ์ง๊ณ ์๋ ๋ฉ๋ชจ๋ฆฌ์์ ๊ฐ์ ๋ณ๊ฒฝ ์ํค๊ณ ์๊ธฐ ๋๋ฌธ์ด๋ค(๊ฐ๋ณ). ๋ถ๋ณ์ฑ์ ์ ์งํ๊ธฐ ์ํด 0์ ๊ฐ์ ๊ฐ์ง ๋ฐ์ดํฐ ์์ญ(๋ผ์ดํธ๋ธ๋ฃจ&๊ทธ๋ ์ด)์์ ์๋ก์ด ์ฃผ์๊ฐ ๋ง๋ค์ด ์ก๊ณ , ๋ณ์b์ ์ฃผ์์์ 0์ ๊ฐ์ ๊ฐ์ง ๋ฐ์ดํฐ์์ญ์ 5001๋ฒ์ ์ฐธ์กฐํ๋ ๊ฒ์ผ๋ก ๋ณ๊ฒฝ๋์๋ค.
๋ฐ์ดํฐ์ ์์ญ์ ์๋ ์ฃผ์์ ๋ฐ์ดํฐ๋ ๋ณ๊ฒฝ ๋์ง ์๋๋ค. ์๋ก ์์ฑ๋ ๋ฟ, ์ด๊ฒ์ด ๋ถ๋ณ์ฑ์ ๋งํ๊ณ ์๋ ๊ฒ์ด๋ค. ๊ทธ๋ฐ๋ฐ ์ด๊ฒ ์ค์ง ๋ฐ์ดํฐ ์์ญ์์ ์ผ์ด๋๊ณ , ๋ฐ์ดํฐ ์์ญ์ ๊ธฐ๋ณธํ ๋ฐ์ดํฐ ํ์ ์ผ๋ก๋ง ์ ์ฅ ๋ ์ ์์ผ๋ฏ๋ก ๊ฒฐ๊ตญ ๊ธฐ๋ณธํ ๋ฐ์ดํฐ๋ ๋ถ๋ณ์ด๋ผ๊ณ ๋ณผ ์ ์๋ค.
๋ฐ์ดํฐ๋ฅผ ๋ด์ ๋ณ์๋ ๋ถ๋ณ์ด ์๋๋ค. ๋ณ์๋ ๋ณ๊ฒฝ๋ ์ ์๋ค. ์๋ ์ด๋ฏธ์ง์ฒ๋ผ ์๋ณ์ b ๋ฅผ ๊ฐ์ง๊ณ ์๋ ์ฃผ์ 1004์ ๊ฐ์ด ์ฃผ์ 5000 ->5001 ๋ก ๋ณ๊ฒฝ๋จ์ผ๋ก์จ ๋ณ์๊ฐ ๋ถ๋ณ์ด ๋๋ ๊ฒ์ ์๋๋ค๋ฅผ ์ฆ๋ช ํ๋ค.
๊ทธ๋ผ ์ฐธ์กฐํ ๋ฐ์ดํฐ๋ ๊ฐ๋ณ์ผ๊น? ๊ธฐ๋ณธํ ๋ฐ์ดํฐ์๋ ์ด๋ป๊ฒ ๋ค๋ฅธ๊ฐ?
์ฌ๊ธฐ์ ์ค์ํ ์ ์ ์์์ ๊ธฐ๋ณธํ์ ๋ถ๋ณ์ด๋ผ๊ณ ํ๋ค๋ฉด, ์ฐธ์กฐํ ๋ฐ์ดํฐ๋ ๊ฐ๋ณ์ ์ธ ์ฑ์ง์ ๋๊ณ ์๋์ง, ๊ธฐ๋ณธํ ๋ฐ์ดํฐ์๋ ์ด๋ป๊ฒ ๋ค๋ฅธ์ง ๊ฐ์ฒด๋ mutable ํ๋ค์ ๋ด๋ถ์ ๋์์ ์์๋ณด์๋ค.
var obj = {
"c" : 0,
"d" : "10"
}
var anotherObj = obj;
anotherObj.d = 0
console.log(obj === anotherObj) // true โ๏ธanotherObj.d ๋ฅผ ๋ณ๊ฒฝํ์์์๋ ๋ถ๊ตฌํ๊ณ obj๋ anotherObj์ ์ผ์นํ๋ค. ์์ผ๊น?
์ฐธ์กฐํ์ด ๊ฐ๋ณ์ ์ฑ์ง์ด ์์์ ์ฆ๋ช
- ๊ฐ์ฒด์ ๋ณ์ ์์ญ์ด ์กด์ฌํ๋ค๋ ์ ์ด๋ค.(3000~). ๊ทธ๋ฆฌ๊ณ ๊ทธ ๋ณ์์ ๊ฐ์ ๊ธฐ์กด ๋ง๋ค์ด ๋์๋ ๋ฐ์ดํฐ 0,10 ์ ๊ทธ๋๋ก ํ์ฉํ๊ณ ์๋ค.
- ๊ฐ์ฒด ๋ด ํ๋กํผํฐ๋ค์ ๊ฐ์ ๊ธฐ๋ณธํ ๊ฐ์ด๋ฏ๋ก ๋ฐ์ดํฐ ์์ญ์ ์ ์ฅ๋ ๋ถ๋ณ ๊ฐ๋ค์ด๋ค. ํ์ง๋ง ๊ฐ์ฒด๋ ๋ฉ๋ชจ๋ฆฌ ๋ณ์ ์์ญ์ ์์ผ๋ฏ๋ก anotherObj.d์ ๊ฐ์ ๋ณ๊ฒฝ ์ฆ, ๋ณ์ 3001 ์ ์๋ 5000์ฃผ์๋ฅผ ์ฐธ์กฐํ๋ ๊ฒ์์ 5001์ ์ฐธ์กฐํ๋ ๊ฒ์ผ๋ก ๋ฐ๋ ๋ฟ ์ด๊ฑธ ์ฐธ์กฐํ๋ ์ฃผ์๊ฐ 2000์ anotherObj,obj๋ ๊ฒฐ๊ตญ ๊ฐ์ ๊ฐ์ ๊ฐ๊ฒ ๋๋ค.
- ์ด๊ฒ ์ฐธ์กฐํ ๋ฐ์ดํฐ๋ ๋ถ๋ณํ์ง ์๋ค ๋ผ๊ณ ๋ณผ ์ ์๋ค.
์์ ์์ ๋ฅผ ํตํด ๊ฐ์ฒด ๋ฐ์ดํฐ ํ์ ์์ ๊ฐ๋ณ์ฑ์ ํ์ธ ํ ์ ์๋ค. ํํธ์ผ๋ก ์ด๋ฌํ ๊ฐ๋ณ์ฑ์ ๋ฌธ์ ์ ์ ์๊ณ ์ค๊ธฐ๋ ํ๋ค. ์๋ณธ๊ฐ์ฒด๊ฐ ๋ฐ๋์ง ๋ง์์ผ ํ ์ํฉ์์ ๋ฌธ์ ๊ฐ ์๊ธด๋ค.
// ๊ฐ์ฒด ๋ฐ์ดํฐ ํ์
์์ ๊ฐ๋ณ์ฑ์ผ๋ก ์ธํ ๋ฌธ์ ์
// ๊ฐ์ฒด ๋ฐ์ดํฐ ํ์
์ ๊ฐ๋ณ์ฑ์ ๊ฐ์ง๊ณ ์๊ธฐ ๋๋ฌธ์ ๋ฌธ์ ๊ฐ ๋ฐ์ํ ์ ์๋ค.
var user = {
name: "Sue",
gender: "male",
};
const changeName = (user, newName) => {
const newUser = user;
newUser.name = newName;
return newUser; // โ๏ธ ๋๋ฆ ์๋ก์ด ๊ฐ์ฒด๋ฅผ ๋ง๋ค์ด์ ๋ฆฌํดํ ๋
ธ๋ ฅ ! ๋ฆฌํดํ๋ค๊ณ ์๊ฐํ ์ ์์ง๋ง, ์ค์ ๋ก๋ user์ newUser๊ฐ ๊ฐ์ ๊ฐ์ฒด๋ฅผ ๊ฐ๋ฆฌํค๊ณ ์๊ธฐ ๋๋ฌธ์ user์ ๊ฐ์ด ๋ณ๊ฒฝ๋๋ ๊ฒ์ด๋ค.
};
const user2 = changeName(user, "Sue2");
if (user !== user2) {
console.log("์ ์ ์ ๋ณด๊ฐ ๋ณ๊ฒฝ๋์์ต๋๋ค.");
}
console.log(user.name, user2.name); // โ๏ธSue2 , Sue2
console.log(user === user2); //โ๏ธ true
์๋ณธ ๊ฐ์ฒด๊ฐ ๋ฐ๋์ง ๋ง์์ผ ํ ์ํฉ์ด๋ผ ํ๋ค๋ฉด ๊ฐ๋ น, ์ ์ ๊ฐ ์ ๋ณด๋ฅผ ๋ณ๊ฒฝํ๋๋ฐ changeName
ํจ์๋ฅผ ํตํด ๋ณ๊ฒฝ ํ๊ณ ๋ ํ์ ๋ฏธ๋ฆฌ๋ณด๊ธฐ ์์๋ ๋ฐ๋์ ๋ณด๋ฅผ, ์ผ๋ฐ ๋ชจ๋์์๋ ๋ณ๊ฒฝ์ ๊ธฐ์กด ์ ์ ์ ๋ณด๋ฅผ ๋์์ ๋ณด์ฌ์ค์ผ ์ํฉ์ด๋ผ๋ฉด,
๋ถ๋ณ ๊ฐ์ฒด๊ฐ ํ์ํ๋ค.
๊ทธ๋ฌ๋๊น ๋ณต์ฌ๋ณธ์ด ์์ ๋๋๋ผ๋ ์๋ณธ์ ์์ ์ด ๋๋ฉด ์๋๋ค. ์์ ๊ฐ์ฒด๊ฐ ๊ฐ์ง ๊ฐ๋ณ์ฑ์ ๋ง๊ธฐ ์ํ ๋ฐฉ๋ฒ์ผ๋ก๋ ๊ฐ์ฒด์ ์๋ก์ด ๊ฐ์ ํ ๋น ํ๋ ๊ฒ์ด๋ค. ํ๋กํผํฐ ๋ณ๊ฒฝ /ํ ๋น์ด ์๋, ์๋ก์ด ๋ฐ์ดํฐ ์์ฒด๋ฅผ ๋งํ๋ค.
const changeName = (user, newName) => {
const newUser = user;
newUser.name = newName;
return newUser; // โ๏ธ ๋๋ฆ ์๋ก์ด ๊ฐ์ฒด๋ฅผ ๋ง๋ค์ด์ ๋ฆฌํดํ ๋
ธ๋ ฅ ! ๋ฆฌํดํ๋ค๊ณ ์๊ฐํ ์ ์์ง๋ง, ์ค์ ๋ก๋ user์ newUser๊ฐ ๊ฐ์ ๊ฐ์ฒด๋ฅผ ๊ฐ๋ฆฌํค๊ณ ์๊ธฐ ๋๋ฌธ์ user์ ๊ฐ์ด ๋ณ๊ฒฝ๋๋ ๊ฒ์ด๋ค.
};
๊ทธ๋ฐ๋ฐ ์ด ์์ ๋ ์ฑ ์์๋ ์ธ๊ธํ๋ฏ์ด, "์ฐธ์กฐํ ๋ฐ์ดํฐ๊ฐ ๊ฐ๋ณ๊ฐ์ด๋ผ๊ณ ์ค๋ช ํ ๋์ ๊ฐ๋ณ์ ์ฐธ์กฐํ ๋ฐ์ดํฐ ์์ฒด๋ฅผ ๋ณ๊ฒฝํ๋ ๊ฒฝ์ฐ๊ฐ ์๋๋ผ ๊ทธ ๋ด๋ถ์ ํ๋กํผํฐ๋ฅผ ๋ณ๊ฒฝํ ๋๋ง ์ฑ๋ฆฝํฉ๋๋ค." ์ ๋ํ ๋ฐ์ฆ์ด๋ค.
๊ฐ๋ณ์ ์ธ ์ฐธ์กฐํ ๋ฐ์ดํฐ๋ ํจ์ ํ๋กํผํฐ๋ง ๋ณ๊ฒฝ ํ๊ธฐ ๋๋ฌธ์ ์ฐธ์กฐํ ๋ฐ์ดํฐ๊ฐ ๊ฐ๋ณ์ ์ด๋ค๋ผ๊ณ ํ ์ ์๋ค. ํ๋กํผํฐ ๋ณ๊ฒฝ์ด ์๋ ์๋ก์ด ๊ฐ์ ๊ฐ์ง ๊ฐ์ฒด๋ฅผ ๋ฆฌํดํ๋ค๋ฉด ๊ฐ๋ณ์ ๋ถ๋ณ์ผ๋ก ๋ง๋ค ์ ์๋ค.
์๋ก์ด ๊ฐ์ฒด๋ฅผ ๋ฆฌํดํ๋ ๋ฐฉ๋ฒ์ผ๋ก๋,
- object literal ๋ฐฉ์
- object literal ๋ฐฉ์์ด ๋ฒ๊ฑฐ๋ก์ฐ๋ ๋ชจ๋ ํ๋กํผํฐ๋ฅผ ๋ณต์ฌํ๋ ํจ์
- Object.create()
- Object.assign()
- object spread operator
๊ฐ ์์ ์ ์๋ค. ๊ทธ๋ฐ๋ฐ ์ด๋ฐ ๋ฐฉ์์ ์ค์ฒฉ๋ ๊ฐ์ฒด์์ ๋ณต์ฌ๊ฐ ๋์ง ์๋๋ค. ๊ทธ ์ด์ ๋ ์ฐธ์กฐํ ๋ฐ์ดํฐ๊ฐ ์ ์ฅ๋ ํ๋กํผํฐ๋ฅผ ๋ณต์ฌํ ๋ ์ฃผ์๊ฐ๋ง ๋ณต์ฌํ๊ธฐ ๋๋ฌธ์ด๋ค. ์ด๋ฅผ ์์ ๋ณต์ฌ๋ผ ํ๋ค. ํด๊ฒฐ๋ฐฉ๋ฒ์ผ๋ก๋ ๊น์ ๋ณต์ฌ ๋ฐฉ๋ฒ์ด ํ์ํ๋ค.
๊น์ ๋ณต์ฌ ๊ตฌํ ๋ฐฉ๋ฒ๋ค
- ํจ์๋ฅผ ์ด์ฉํ์ฌ ๋ด๋ถ ํ๋กํผํฐ๋ค์ ์ผ์ผ์ด ์ํํ๋ค. ๋ง์ฝ ํ๋กํผํฐ๊ฐ ๊ฐ์ฒด๋ผ๋ฉด ๊ทธ ๊ฐ์ฒด์ ํ๋กํผํฐ๋ค์ ๋ค์ ์ํํ์ฌ ๊ฐ๋ค์ ๋ณต์ฌํ๋ ๋ฐฉ๋ฒ.
- JSON.parse(JSON.stringify( object )) ์ด์ฉ
- (์ฑ ์๋ ์์ง ๊ธฐ์ฌ๋์ง ์์) WebAPIs ์์ ์ ์ํ structuredClone() .MDN structuredClone ์ฐธ๊ณ
- Lodashโs cloneDeep()
์ ๋ฆฌํ๋ฉฐ
๋ถ๋ณ์ฑ์ ์ ์งํ๊ธฐ ์ํ ๋ฐฉ๋ฒ์ผ๋ก ์์ ๋ค์ด์ค๋ ํจ์ํ ํ๋ก๊ทธ๋๋ฐ์ด๋ ์ฑ ์์๋ ์นดํผ-์จ-๋ผ์ดํธ์ ๋ฐฉ์ด์ ๋ณต์ฌ๋ฅผ ์๊ฐ ํ๋ค. ํนํ๋ ๋ ๊ฑฐ์ ์ฝ๋๋ ์ ๋ขฐํ ์ ์๋ ์ฝ๋๋ก๋ถํฐ ๋ถ๋ณ์ฑ์ ์งํค๋ ๋ฐฉ๋ฒ์ ๋ํด ์ค๋ช ํ๋๋ฐ, ์ค๋ ํฌ์คํ ์ผ๋ก ๊ฐ์ฒด์์ ๊ฐ๋ณ์ฑ์ ์๋ฆฌ๋ฅผ ์์์ผ๋ ์ฐ์ฅ์ ์ผ๋ก ์ข์ ๋ฐฐ์์ด ๋ ๊ฒ ๊ฐ๋ค.