06 기본적인 리팩터링 - 변수 이름 바꾸기
변수 이름 바꾸기
let a = height * width;
▼
let area = height * witdh;
배경
명확한 프로그래밍의 핵심은 이름짓기다. 변수는 프로그래머가 하려는 일에 관해 많은 것을 설명해준다. 단, 이름을 잘 지었을 때만 그렇다. 사실 나는 이름을 잘못 지을 때가 많다. 고민을 충분히 하지 않아서거나, 개발을 더 하다 보니 문제에 대한 이해도가 높아지거나, 혹은 사용자의 요구가 달라져서 프로그램의 목적이 변해 그럴 때도 있다.
특히 이름의 중요성은 그 사용 범위에 영향을 많이 받는다. 한 줄짜리 람다식lambda expression에서 사용하는 변수는 대체로 쉽게 파악할 수 있다. 맥락으로부터 변수의 목적을 명확히 알 수 있어서 한 글자로 된 이름을 짓기도 한다. 마찬가지로 간단한 함수의 매개변수 이름도 짧게 지어도 될 때가 많다. 물론 자바스크립트와 같은 동적 타입 언어라면 나는 이름 앞에 타입을 드러내는 문자를 붙이는 스타일을 선호한다(가령 매개변수 이름을 aCustomer와 같이 짓는다).
함수 호출 한 번으로 끝나지 않고 값이 영속되는 필드라면 이름에 더 신경 써야 한다. 내가 가장 신중하게 이름 짓는 대상이 바로 이런 필드들이다.
절차
- 폭넓게 쓰이는 변수라면 변수 캡슐화하기를 고려한다.
- 이름을 바꿀 변수를 참조하는 곳을 모두 찾아서, 하나씩 변경한다.
- → 다른 코드베이스에서 참조하는 변수는 외부에 공개된 변수이므로 이 리팩터링을 적용할 수 없다.
- → 변수 값이 변하지 않는다면 다른 이름으로 복제본을 만들어서 하나씩 점진적으로 변경한다. 하나씩 바꿀 때마다 테스트한다.
- 테스트한다.
예시
변수 이름 바꾸기의 가장 간단한 예는 임시 변수나 인수처럼 유효범위가 함수 하나로 국한된 변수다. 굳이 예시가 필요 없을 정도로 간단하다. 그저 변수를 참조하는 코드를 찾아서 하나씩 바꾸면 되며, 다 바꾼 뒤에는 테스트해서 실수한 부분은 없는지 확인한다.
함수 밖에서도 참조할 수 있는 변수라면 조심해야 한다. 코드베이스 전체에서 두루 참조할 수도 있다. 다음 변수에서 이야기를 시작해보자.
let tpHd = 'untitled';
어떤 참조는 다음과 같이 변수를 읽기만 한다.
result += `<h1>${tpHd}</h1>`;
값을 수정하는 곳도 있다고 해보자.
tpHd = obj['articleTitle'];
나는 이럴 때 주로 변수 캡슐화하기로 처리한다.
setTitle(obj['articleTitle']);
function title() { // tpHd 변수의 게터
return tpHd;
}
function setTitle(arg) { // tpHd 변수의 세터
tpHd = arg;
}
캡슐화 후에는 변수 이름을 바꿔도 된다.
let _title = 'untitled';
function title() {
return _title;
}
function setTitle(arg) {
_title = arg;
}
그런 다음 래핑 함수들을 인라인해서 모든 호출자가 변수에 직접 접근하게 하는 방법도 있지만, 나는 별로 내켜하지 않는 방식이다. 이름을 바꾸기 위해 캡슐화부터 해야 할 정도로 널리 사용되는 변수라면 나중을 위해서라도 함수 안에 캡슐화된 채로 두는 편이 좋다고 생각하기 때문이다.
함수를 인라인한다면 값을 얻을 때는 getTitle() 게터를 호출하고 변수 이름에는 밑줄(_)을 붙이지 않았을 것이다.
예시: 상수 이름 바꾸기
상수(또는 클라이언트가 볼 때 상수처럼 작용하는 대상)의 이름은 캡슐화하지 않고도 복제 방식으로 점진적으로 바꿀 수 있다. 상수가 다음처럼 선언되어 있다고 하자.
const cpyNm = '애크미 구스베리';
먼저 원본의 이름을 바꾼 후, 원본의 원래 이름(기존 이름)과 같은 복제본을 만든다.
const companyName = '애크미 구스베리';
const cpyNm = companyName;
이제 기존 이름(복제본)을 참조하는 코드들을 새 이름으로 점진적으로 바꿀 수 있다. 다 바꿨다면 복제본을 삭제한다. 나는 기존 이름을 삭제했다가 테스트에 실패하면 되돌리는 방식보다 (앞의 코드처럼) 새 이름으로 선언한 다음 기존 이름에 복사하는 방식이 조금이라도 쉽다면 후자를 선택한다.
이 방식은 상수는 물론, 클라이언트가 볼 때 읽기전용인 변수(가령 자바스크립트의 익스포트한 변수)에도 적용할 수 있다.
[출처]
리팩터링 2판 - 마틴 파울러
[정리]
변수 이름 바꾸는 리팩터링을 실행할 때는 변수 캡슐화하기처럼 역시 바꾸는 값을 독점하는 함수를 만든다. (get, set) 상수 이름을 바꿀 때는 먼저 원본 변수의 이름을 바꾼 후 원본 변수의 값을 참조하는 변수를 만든다.