원본 주소: PHP Talk "리팩토링 - 기존 코드의 디자인 개선" 1부 기능 재구성
마인드맵
아래 이미지를 클릭하시면 더 큰 이미지를 보실 수 있습니다.
소개
내가 가장 좋아하고 관심 있는 것들을 적어서 여러분과 공유합니다. 지난번에 나는 "PHP와 상사 사이의 대화"라는 기사를 썼습니다. 아직도 궁금한 게 많은데 이 책이 도움이 많이 됐어요.
바빠서 글을 읽기 힘드신 분들은 스크린샷만 보시면서 많은 이득을 얻으시길 권합니다. 스크린샷의 코드를 비교하면 어느 것이 더 나은지 알 수 있습니다.
코드 부분에 왜 그림을 사용하나요? 코드를 읽을 때 휴대폰을 자주 사용하기 때문에 블로그 파크의 코드가 휴대폰에 지저분해서 사진을 보는 것이 더 편합니다.
전문용어
결국 우리는 코딩에 영문자를 사용하기 때문에 영어 단어를 사용하는 것이 우리의 전문성을 더 잘 보여줄 수 있습니다. 다음 영어 단어를 마스터하면 다른 코더들과 소통할 때 더욱 직접적이고 전문적으로 소통할 수 있을 것입니다. ——우리의 악취를 자랑하자, 하하.
“*”는 본문에서 자주 언급되는
을 나타냅니다.
인라인: 인라인
함수: 함수
*방법: 방법
세밀한:세밀한
이름 바꾸기: 이름 바꾸기
쿼리: 쿼리
temp: 임시(임시) - 일반적으로 임시 변수를 나타냅니다
*추출:추출 - 개인적으로 "정제"로 번역하는 것을 선호합니다
*복제: 복사
분할:해부학
변수: 변수
인수: 요인, 요인
재구성 원리
1. 재건축이란 무엇인가요?
명사형: 소프트웨어의 관찰 가능한 동작을 변경하지 않고 이해성을 높이고 수정 비용을 줄이기 위한 목적으로 소프트웨어의 내부 구조를 조정합니다.
동사 형태: 일련의 리팩토링 원칙을 사용하여 관찰 가능한 동작을 변경하지 않고 소프트웨어 구조를 조정합니다.
2. 리팩터링을 하는 이유는 무엇인가요?
1. 리팩토링을 자주 하면 코드를 올바른 형식으로 유지할 수 있습니다.
2. 코드가 적절한 위치를 찾도록 합니다.
3. 소프트웨어를 이해하기 쉽게 만듭니다.
4. 버그가 발견될 수 있습니다.
5. 인코딩 속도를 향상시킵니다.
3. 재건축의 문제
1. 인터페이스 이름 수정
클래스의 메서드가 공개인 경우 이름을 바꾸면 어떤 모듈이 메서드를 호출하는지 알 수 없게 됩니다. 일반적인 접근 방식은 전체 프로젝트에서 메서드 이름을 바꾸는 것입니다. grep 작업을 수행한 다음 각 모듈의 호출과 로직을 하나씩 살펴봅니다. ——그래서 우리는 클래스를 작성할 때 인터페이스가 열리지 않도록 속성과 메서드를 비공개로 설정하려고 합니다.
2. 리팩토링하지 말아야 할 경우
(1) 코드를 모두 다시 작성하고 기존 코드가 너무 헷갈리기 때문에 다시 작성하는 것보다 리팩토링하는 것이 좋습니다.
(2) 프로젝트가 거의 끝나갈 무렵에는 리팩토링을 피해야 합니다. 이를 해결하기 위해 재구성을 두 번째 단계에 넣을 수 있습니다.
나쁜 코드 냄새
1. 중복 코드
1. 동일한 클래스의 두 메소드에 동일한 표현식이 포함되어 있습니다.
해결 방법: Extract Method를 사용하여 중복 코드를 추출한 다음 두 메소드 모두 이 Extract Method를 호출하도록 할 수 있습니다.
2. 두 클래스의 메소드가 비슷합니다.
해결 방법: (1) 두 클래스의 메서드를 제시하고 공동으로 상위 클래스를 구성합니다.
(2) 한 클래스의 메소드를 삭제하고 다른 클래스의 메소드를 호출합니다.
2. 긴 방법
1. 짧은 함수: 서브루틴이 수행하는 작업을 보려면 컨텍스트를 자주 전환해야 하기 때문에 코드를 읽는 데 약간의 노력이 필요합니다. 그러나 작은 방법을 이해하기 쉽게 만드는 진짜 열쇠는 좋은 이름입니다. 독자는 함수에 쓰여진 내용을 읽지 않고도 이름을 통해 함수의 기능을 이해할 수 있습니다. ——초기 프로그래밍 언어에서는 메서드 호출에 추가 오버헤드가 필요했기 때문에 코더는 작은 메서드 사용을 꺼렸습니다. 그러나 현대 OO 언어는 프로세스 내에서 추가 오버헤드(함수 호출)를 거의 완전히 제거했습니다.
2. 댓글에서 신호 추출: 무언가를 설명하기 위해 댓글을 사용해야 한다고 느낄 때마다 설명해야 할 내용을 독립적인 함수에 작성하고 목적에 따라 이름을 지정합니다. 이는 코드 그룹을 사용하거나 단 한 줄의 코드로도 수행할 수 있습니다. - 함수 이름이 사용자를 설명하는 한, 주저하지 말고 그렇게 하십시오.
"기능"은 "무엇을 해야 할지" 또는 "어떻게 해야 할지"로 이해됩니다.
3. 조건식과 루프는 정제 신호인 경우가 많습니다.
4. "코드 청결성"의 예. 우리는 그것에 대해 생각할 수 있습니다!
3. 대규모 수업
1. Class에 포함된 여러 속성 변수의 접두사 또는 접미사가 동일한 경우 Extract Class를 사용할 수 있습니다.
2. Class의 대부분의 변수는 속성변수를 사용하지 않으며, Extract Class를 사용하면 됩니다.
3. 코드가 너무 많으면 클래스를 추출할 수 있습니다.
4. 긴 매개변수
매개변수 개체를 소개합니다. ——저는 이에 동의하지 않습니다. 왜냐하면 저는 다른 사람의 메소드를 사용할 때 제가 원하는 데이터를 얻기 위해 거기에 사용된 객체의 속성이나 메소드를 보는 것은커녕 코드 실습도 거의 보지 않기 때문입니다.
5. 스위치 설명
1. 스위치 문을 적게 사용하세요. ——문제는 중복이다. 새 케이스를 추가할 때는 모든 케이스를 찾아서 수정해야 합니다.
2. 다형성으로 대체합니다. 방법: 1. 스위치에서 Extract Method를 수행합니다. 2. MoveMethod는 케이스의 실제 코드를 다형성 클래스에 넣습니다.
6. 댓글
Extract Method를 사용해 보세요. 그래도 작동하지 않으면 Rename Method를 사용해 보세요.
댓글을 작성해야 한다고 생각되면 먼저 리팩토링을 시도하고 모든 댓글을 중복되도록 만드세요.
댓글은 일반적으로 향후 계획에 사용되며, 완전히 확신할 수 없는 부분(무언가를 수행하는 이유)에 사용될 수도 있습니다.
Long Method에는 너무 많은 정보가 포함되어 복잡한 논리로 덮여 식별하기 어려운 경우가 많습니다.
1. 추출방법
상황: 함수가 너무 길거나 목적을 이해하기 위해 주석이 필요한 코드가 보입니다. 그런 다음 이 코드를 별도의 함수에 넣고 함수 이름으로 함수의 목적을 설명하도록 합니다.
동기:
짧고 이름이 잘 지정된 함수: --finely graned
1. 재사용 가능성이 높습니다.
2. 이 함수는 일련의 주석처럼 읽혀집니다.
3. 기능 덮어쓰기가 쉽습니다.
핵심 포인트: 함수 길이의 핵심은 함수 이름과 함수 온톨로지 사이의 의미론적 거리에 있습니다. 개선 작업을 통해 코드의 명확성이 향상된다면 그렇게 하십시오.
방법:
1. 새 함수를 만들고 함수의 목적에 따라 이름을 지정합니다. "어떻게" 수행하는지보다는 "무엇을" 수행하는지에 따라 이름을 지정합니다.
=》 메시지나 함수 호출 등 추출 함수가 매우 간단하더라도 새 함수가 코드 의도를 더 나은 방식으로 표현할 수 있는 한 추출해야 합니다. 하지만 더 의미 있는 이름이 생각나지 않는다면 그대로 두십시오.
2. 소스 함수에서 추출 코드를 새 함수로 이동합니다.
2. 인라인 방식
메소드 이름만큼 메소드 본문이 명확하고 이해하기 쉬우면 인라인 메소드를 사용하세요.
3. 인라인 온도
임시변수는 단순 표현식으로 한 번만 할당되며, 할당 후에는 한 번만 사용됩니다. ——온도를 인라인으로 올려주세요
4. 임시를 쿼리로 대체
임시 변수에 표현식이 포함된 경우 표현식 추출 방법이 사용됩니다. ——이것이 바로 쿼리식, 쿼리
동기:
1. 지역 변수는 코드를 수정하기 어렵게 만듭니다.
2. 임시 변수를 사용하면 더 긴 코드를 작성해야 합니다. 쿼리 메소드로 변경하면 클래스 하위 메소드에서 해당 정보를 얻을 수 있다. - 더 깔끔한 코드를 작성하겠습니다.
3. Extract Method를 사용하기 전에 Temp를 Query로 바꾸는 것이 필수적인 단계인 경우가 많습니다.
방법:
1. 한 번만 할당된 임시 변수를 찾습니다.
=> 임시 변수가 두 번 이상 할당된 경우 임시 변수 분할을 사용하여 여러 변수로 분할하는 것을 고려해보세요.
2. 임시변수 할당의 오른쪽 부분을 독립된 함수로 추출합니다.
=> 메소드를 비공개로 선언한 다음 나중에 다른 클래스에서 사용하는 경우 공개 또는 보호를 해제합니다.
코드가 잘 구성되어 있으면 더 효과적인 최적화 솔루션을 찾을 수 있는 경우가 많습니다. ————성능이 정말 안 좋으면 되돌리기 쉽습니다.
5. 설명변수 소개
복잡한 표현식의 결과(또는 그 일부)를 임시 변수에 넣고 변수 이름을 사용하여 표현식의 목적을 설명합니다.
동기:
표현이 복잡하고 읽기 어렵습니다. 이 경우 임시 변수는 표현식을 보다 관리하기 쉬운 형식으로 나누는 데 도움이 될 수 있습니다.
6. 임시변수 분할
임시 변수가 두 번 이상 할당되었습니다. 루프 변수도 아니고 설정 변수도 아닙니다. 그런 다음 은 각 할당에 대해 독립적이고 해당하는 임시 변수를 만듭니다.
동기:
1. 임시 변수가 여러 역할을 담당하는 경우 여러 임시 변수로 대체해야 합니다. 각 변수에는 하나의 책임만 있습니다.
2. 동일한 임시 변수가 두 가지 다른 일을 담당하므로 리뷰가 혼란스러워집니다.
6. 매개변수 할당 제거
코드에서 매개변수를 할당하는 경우 매개변수 위치를 임시 변수로 바꿉니다.
7. 메소드를 메소드 객체로 대체
큰 함수에서 지역 변수를 사용할 때는 Extract Method를 사용할 수 없습니다. 그런 다음 이 메소드를 별도의 객체에 넣어 지역 변수가 객체의 필드가 되도록 한 다음 동일한 객체에서 큰 함수를 여러 개의 작은 메소드로 분해합니다.
동기:
1. 대규모 메소드에서 상대적으로 독립적인 코드를 추출하면 코드의 가독성이 크게 향상될 수 있습니다.
2. Method에는 지역 변수가 너무 많아서 이 함수를 분해하기가 매우 어렵습니다.
3. 메소드를 메소드 객체로 대체하면 모든 지역 변수가 객체의 값 범위로 변경됩니다. 그런 다음 이 새 객체에 대해 Extract Method를 수행합니다.
8. 대체 알고리즘
알고리즘을 더 깨끗한 다른 알고리즘으로 교체하려면 메소드 본문을 다른 알고리즘으로 교체하세요. ——원래 Method Body를 직접 수정하면 됩니다.
동기 부여: 문제에 대해 더 많이 배우고 더 명확한 방법으로 무언가를 수행할 수 있다는 것을 알게 되면 복잡한 방법을 더 명확한 방법으로 바꿔야 합니다.
요약
이것은 이 책의 내용 중 일부일 뿐입니다. 저를 포함하여 많은 코더들이 매우 동의하고 일부는 동의하지 않을 것이라는 점을 알고 있습니다. 그러므로 우리는 “좋은 것은 따르고 나쁜 것은 바로잡”아야 합니다.
자신의 의견을 자유롭게 표현해 주세요.