getter / setter 메서드가 아닌 객체 메서드 내에서 객체 속성에 액세스하는 “순수 적”또는 “올바른”방법은 무엇입니까?
객체 외부에서 getter / setter를 사용해야한다는 것을 알고 있지만 내부에서는 다음과 같이하면됩니다.
자바:
String property = this.property;
PHP :
$property = $this->property;
또는 당신은 할 것 :
자바:
String property = this.getProperty();
PHP :
$property = $this->getProperty();
제 Java가 약간 벗어난 경우 용서하십시오. Java로 프로그래밍 한 지 1 년이 지났습니다.
편집하다:
사람들은 내가 개인 또는 보호 변수 / 속성에 대해서만 이야기하고 있다고 가정하고있는 것 같습니다. 내가 OO를 배웠을 때 나는 그것이 공개 된 경우에도 모든 단일 속성에 대해 getter / setters를 사용하도록 배웠습니다 (실제로 나는 어떤 변수 / 속성도 공개하지 말라고 들었습니다). 그래서 나는 처음부터 잘못된 가정에서 출발 할 수 있습니다. 이 질문에 대답하는 사람들은 아마도 당신이 공공 자산을 가져야한다고 말하는 것 같습니다. 그리고 그것들은 내가 배운 것과 내가 말한 것과 반대되는 게터와 세터가 필요하지 않다고 말하는 것 같습니다. 잘. 그것은 아마도 다른 질문에 대한 좋은 주제 일 것입니다 …
답변
이것은 종교적 전쟁 가능성이 있지만 getter / setter를 사용하는 경우 내부적으로도 사용해야하는 것 같습니다. 둘 다 사용하면 향후 유지 관리 문제가 발생할 수 있습니다 (예 : 누군가 필요한 setter에 코드를 추가 합니다). 해당 속성이 설정 될 때마다 실행되고 속성은 해당 setter가 호출되지 않고 내부적으로 설정됩니다.
답변
개인적으로 일관성을 유지하는 것이 중요하다고 생각합니다. 게터와 세터가 있으면 사용하십시오. 내가 필드에 직접 액세스하는 유일한 시간은 접근자가 많은 오버 헤드를 가질 때입니다. 불필요하게 코드가 부풀어 오르는 것처럼 느껴질 수 있지만 앞으로는 많은 두통을 확실히 줄일 수 있습니다. 고전적인 예 :
나중에 필드가 작동하는 방식을 바꾸고 싶을 수 있습니다. 즉석에서 계산해야하거나 백업 저장소에 다른 유형을 사용하고 싶을 수도 있습니다. 속성에 직접 액세스하는 경우 이와 같은 변경은 한 번에 엄청난 양의 코드를 깨뜨릴 수 있습니다.
답변
그 정서가 만장일치로 놀랍습니다. getters
이고 세터가 훌륭하고 훌륭 . 나는 Allen Holub의 ” Getters And Setters Are Evil ” 의 방화 기사를 제안합니다 . 물론 제목은 충격적인 가치를위한 것이지만 저자는 타당한 지적을합니다.
기본적으로, 당신이있는 경우 getters
및setters
각각의 모든 개인 필드, 공용 좋은으로 해당 필드를 만들고있다. 당신은 그것을 호출하는 모든 클래스에 파급 효과없이 private 필드의 유형을 변경하기가 매우 어려울 것입니다 getter
.
더욱이, 엄격하게 OO 관점에서 객체는 (희망적으로) 단일 책임에 해당하는 메시지 (메소드)에 응답해야합니다. 대부분의 getters
및 setters
구성 개체에 대해 의미가 없습니다.Pen.dispenseInkOnto(Surface)
나보다 더 의미가 Pen.getColor()
있습니다.
게터와 세터는 또한 클래스 사용자가 개체에 데이터를 요청하고 계산을 수행 한 다음 절차 적 프로그래밍으로 더 잘 알려진 개체에 다른 값을 설정하도록 권장합니다. 처음에하려고했던 것을 단순히 대상에게 지시하는 것이 더 낫습니다. 정보 전문가 라고도 함 관용구 .
그러나 게터와 세터는 UI, 지속성 등 레이어 경계에서 필요한 악입니다. C ++의 friend 키워드, Java의 패키지 보호 액세스, .NET의 내부 액세스 및 Friend Class Pattern 과 같은 클래스의 내부에 대한 제한된 액세스 는 getters
이를 필요로하는 사람들에게만 가시성 과 setter를 줄이는 데 도움이 될 수 있습니다.
답변
속성이 어떻게 사용되는지에 따라 다릅니다. 예를 들어 이름 속성이있는 학생 개체가 있다고 가정합니다. 아직 검색되지 않은 경우 Get 메서드를 사용하여 데이터베이스에서 이름을 가져올 수 있습니다. 이렇게하면 데이터베이스에 대한 불필요한 호출을 줄일 수 있습니다.
이제 개체에 이름이 호출 된 횟수를 계산하는 개인 정수 카운터가 있다고 가정 해 보겠습니다. 개체 내부에서 Get 메서드를 사용하면 잘못된 개수가 생성되므로 사용하지 않는 것이 좋습니다.
답변
PHP는 마법 방법을 포함하여이 처리 할 수있는 방법의 무수 제공 __get
등을 __set
,하지만 난 명시 적 getter 및 setter를 선호합니다. 그 이유는 다음과 같습니다.
- 유효성 검사는 setter (및 해당 문제에 대한 getter)에 배치 할 수 있습니다.
- Intellisense는 명시 적 방법으로 작동합니다.
- 속성이 읽기 전용인지, 쓰기 전용인지 또는 읽기-쓰기인지에 대한 질문 없음
- 가상 속성 (즉, 계산 된 값)을 검색하는 것은 일반 속성과 동일하게 보입니다.
- 실제로 어디에도 정의되지 않은 객체 속성을 쉽게 설정할 수 있으며 문서화되지 않습니다.
답변
여기서 배 밖으로 나가는 건가요?
혹시 😉
또 다른 접근 방식은 개인 / 보호 방법을 사용하여 실제로 가져 오기 (캐싱 / db / etc)를 수행하고 개수를 증가시키는 공용 래퍼를 사용하는 것입니다.
PHP :
public function getName() {
$this->incrementNameCalled();
return $this->_getName();
}
protected function _getName() {
return $this->name;
}
그런 다음 객체 자체 내에서 :
PHP :
$name = $this->_getName();
이 방법을 사용하면 여전히 첫 번째 인수를 다른 항목에 사용할 수 있습니다 (예 : 여기에서 캐시 된 데이터를 사용할지 여부에 대한 플래그를 보내는 것과 같은).
답변
여기서 요점을 놓치고 있어야합니다. 객체 내부에서 getter를 사용하여 해당 객체의 속성에 액세스하는 이유는 무엇입니까?
결론에 도달하면 getter는 getter를 호출해야하며 getter를 호출해야합니다.
따라서 객체 메서드 내부에서 속성에 직접 액세스한다고 말하고 싶습니다. 특히 해당 객체에서 다른 메서드를 호출하는 것으로 보는 것 (어쨌든 속성에 직접 액세스 한 다음 반환)은 무의미하고 낭비적인 연습 일뿐입니다 (또는 질문을 오해 했습니까? ).