안녕하세요. 박민성입니다. ☺️
오늘은 C#의 ref local, ref return대해서 글을 쓰고자 합니다. 🤔
1. 일반 대입은 값을 복사합니다.
int[] numbers = { 10, 20, 30 };
int val = numbers[0];
val = 100;
배열의 값을 변수에 가져오면 보통 값이 복사됩니다.
val은 100이고 numbers[0]은 10입니다.
val의 값을 바꾼다고 해서 numbers[0]은 변하지 않습니다.
val는 numbers[0]의 값을 복사했을 뿐이라서 서로 별개이기 때문입니다.
2. ref local이란?
ref local은 값을 복사하지 않고 기존 변수의 저장 위치를 직접 참조하는 지역 변수입니다. 약간 C++에 포인터가 생각나는 문법입니다.
int[] numbers = { 10, 20, 30 };
ref int val = ref numbers[0];
이 코드는 val는 새로운 int 값을 가진 변수가 아니라 numbers[0] 자체를 가리키게 됩니다.
그럼
val = 100;
Debug.Log(numbers[0]); // 100
이렇게 val을 바꾸면 numbers[0]가 바뀌게 됩니다. 둘이 같은 저장 공간을 바라보는 것인 겁니다.
그렇기 대문에
val++;
numbers[0]++; // 똑같음
이 두 줄은 같은 결과가 나옵니다.
여기서 ref local을 사용할 때
ref int val = ref numbers[0];
앞이랑 뒤 둘다 ref를 작성해야 합니다.
앞 ref는 val이 참조 지역 변수인 것을 뜻하고 뒤 ref는 오른쪽 값을 복사하지 말고 해당 저장 위치를 참조하라는 뜻입니다.
3. ref return이란?
private int GetFirst(int[] numbers)
{
return numbers[0];
}
보통 메서드는 값을 반환합니다.
int value = GetFirst(numbers);
이렇게 호출하면 numbers[0]의 값이 복사돼서 반환됩니다.
private ref int GetFirst(int[] numbers)
{
return ref numbers[0];
}
하지만 반환형 앞에 ref를 붙이면 값이 아니라 원본 저장 위치를 반환할 수 있습니다!
ref int val = ref GetFirst(numbers);
이렇게 호풀할 수 있습니다.
이제 val는 원본 배열 요소를 직접 참조하기 때문에
val = 500;
Debug.Log(numbers[0]); // 500
이런식으로 val 값을 바꾸면 numbers[0]도 바뀌게 됩니다.
여기서!!
아무 변수나 ref return할 수 있는 건 아닙니다.
private ref int GetValue()
{
int number = 10;
return ref number; // 오류
}
이렇게는 사용할 수 없습니다.
왜냐하면 number는 메서드의 지역 변수라서 메서드가 끝나면 더 이상 사용할 수 없기 때문입니다.
4. ref readonly
ref readonly int value = ref numbers[0];
원본을 참조하되 수정은 못 하게 만들 수도 있습니다.
Debug.Log(value); // OO
value = 100; // XX
읽니는 가능하지만 수정은 불가능합니다.
큰 구조체를 복사하지 않고 읽기만 하고 싶을 때 유용합니다.
오늘은 C#에 ref local, ref return에 대해서 알아보았는데요~!
Unity 개발하면서 유용하게 사용될 듯 싶습니다.
기본적인 int, float 자료형이 아닌 struct를 사용할 때 많이 사용할 듯 생각이 듭니다.
큰 구조체를 사용할 때 최적화 용도로 사용하지 않을까여?
오늘의 노래 추천은
CORTIS (코르티스) - REDRED 이라는 곡입니다.
팔랑귀 팔랑귀 (That's red, red)
눈치나 살피기 (That's red, red)
도가니 사리기 (That's red, red)
넘어가 울타리 green, green
내일은 더욱 좋은 글을 써보도록 노력하겠습니다.
봐주셔서 감사합니다. ☺️