protected function getClassDistance(
        string $childClass,
        string $parentClass
    ): int {
        if ($childClass === $parentClass) {
            return 0;
        }

        $result = 0;
        $childParents = class_parents($childClass, true);
        foreach($childParents as $childParent) {
            $result++;
            if ($childParent === $parentClass) {
                return $result;
            }
        }

        // We'll treat implementing an interface as having a greater class
        // distance. This because we want a concrete implementation to be more
        // specific than an interface. For example, suppose we have:
        // - FooInterface
        // - FooClass, implementing the above interface
        // If a mapping has been registered for both of these, we want the
        // mapper to pick the mapping registered for FooClass, since this is
        // more specific.
        $interfaces = class_implements($childClass);
        if (\in_array($parentClass, $interfaces, true)) {
            return ++$result;
        }

        // @todo: use a domain specific exception.
        throw new \Exception(
            'This error should have never be thrown.
            This could only happen if given childClass is not a child of the given parentClass'
        );
    }