정적 코드 검사로 유형 일관성을 감지 할 수있는 PHP의 제네릭 부족에 대한 적절한 해결책이 있습니까?
나는 서브 클래스를 만들고 싶어하는 추상 클래스를 가지고 있으며 메소드 중 하나가 한 유형의 매개 변수를 취하는 것에서 해당 매개 변수의 하위 클래스 인 매개 변수를 취하는 것으로 변경하도록 강요합니다.
abstract class AbstractProcessor {
abstract function processItem(Item $item);
}
class WoodProcessor extends AbstractProcessor {
function processItem(WoodItem $item){}
}
허용되지 않는 메소드 서명을 변경하기 때문에 PHP에서는 허용되지 않습니다. Java 스타일 제네릭을 사용하면 다음과 같은 작업을 수행 할 수 있습니다.
abstract class AbstractProcessor<T> {
abstract function processItem(T $item);
}
class WoodProcessor extends AbstractProcessor<WoodItem> {
function processItem(WoodItem $item);
}
그러나 분명히 PHP는이를 지원하지 않습니다.
이 문제에 대한 Google의 경우 사람들 instanceof
은 런타임시 오류를 확인 하는 데 사용 하는 것이 좋습니다.
class WoodProcessor extends AbstractProcessor {
function processItem(Item $item){
if (!($item instanceof WoodItem)) {
throw new \InvalidArgumentException(
"item of class ".get_class($item)." is not a WoodItem");
}
}
}
그러나 런타임에만 작동하므로 정적 분석을 사용하여 코드에서 오류를 검사 할 수 없으므로 PHP에서이를 처리하는 합리적인 방법이 있습니까?
보다 완벽한 문제의 예는 다음과 같습니다.
class StoneItem extends Item{}
class WoodItem extends Item{}
class WoodProcessedItem extends ProcessedItem {
function __construct(WoodItem $woodItem){}
}
class StoneProcessedItem extends ProcessedItem{
function __construct(StoneItem $stoneItem){}
}
abstract class AbstractProcessor {
abstract function processItem(Item $item);
function processAndBoxItem(Box $box, Item $item) {
$processedItem = $this->processItem($item);
$box->insertItem($item);
}
//Lots of other functions that can call processItem
}
class WoodProcessor extends AbstractProcessor {
function processItem(Item $item) {
return new ProcessedWoodItem($item); //This has an inspection error
}
}
class StoneProcessor extends AbstractProcessor {
function processItem(Item $item) {
return new ProcessedStoneItem($item);//This has an inspection error
}
}
Item
to를 전달 new ProcessedWoodItem($item)
하고 있으며 WoodItem을 매개 변수로 사용하기 때문에 코드 검사에서 오류가 있음을 나타냅니다.