public static function createFromItems(array $items, Grammar $grammar): self
    {
        $final_items = [];
        $new_items = $items;
        /** @var Symbol $known_next_symbols */
        $known_next_symbols = [];
        while ($new_items) {
            /** @var Symbol $next_symbols */
            $next_symbols = [];
            foreach ($new_items as $new_item) {
                foreach ($final_items as $item) {
                    if (0 === Item::compare($item, $new_item)) {
                        goto NEXT_NEW_ITEM;
                    }
                }
                $final_items[] = $new_item;

                $next_symbol = $new_item->getExpected();
                if (!$next_symbol || $next_symbol->isTerminal()) {
                    continue;
                }
                $name = $next_symbol->getName();
                if (isset($known_next_symbols[$name])) {
                    continue;
                }
                $next_symbols[$name] = $next_symbol;

                NEXT_NEW_ITEM:
            }

            $known_next_symbols += $next_symbols;

            $new_items = [];

            foreach ($next_symbols as $next_symbol) {
                $rules = $grammar->getRulesFor($next_symbol);
                foreach ($rules as $rule) {
                    $new_items[] = Item::createFromRule($rule);
                }
            }
        }

        return new static($final_items, $items, $grammar);
    }
public static function createFromItems(array $items, Grammar $grammar): self
    {
        $final_items = [];
        $new_items = $items;
        /** @var Symbol $known_next_symbols */
        $known_next_symbols = [];
        while ($new_items) {
            /** @var Symbol $next_symbols */
            $next_symbols = [];
            foreach ($new_items as $new_item) {
                foreach ($final_items as $item) {
                    if (0 === Item::compare($item, $new_item)) {
                        goto NEXT_NEW_ITEM;
                    }
                }
                $final_items[] = $new_item;

                $next_symbol = $new_item->getExpected();
                if (!$next_symbol || $next_symbol->isTerminal()) {
                    continue;
                }
                $name = $next_symbol->getName();
                if (isset($known_next_symbols[$name])) {
                    continue;
                }
                $next_symbols[$name] = $next_symbol;

                NEXT_NEW_ITEM:
            }

            $known_next_symbols += $next_symbols;

            $new_items = [];

            foreach ($next_symbols as $next_symbol) {
                $rules = $grammar->getRulesFor($next_symbol);
                foreach ($rules as $rule) {
                    $new_items[] = Item::createFromRule($rule);
                }
            }
        }

        return new static($final_items, $items, $grammar);
    }
public static function createFromItems ( array $ items , Grammar $ grammar ) : self { $ final_items = [ ] ; $ new_items = $ items ; /** @var Symbol $known_next_symbols */ $ known_next_symbols = [ ] ; while ( $ new_items ) { /** @var Symbol $next_symbols */ $ next_symbols = [ ] ; foreach ( $ new_items as $ new_item ) { foreach ( $ final_items as $ item ) { if ( 0 === Item :: compare ( $ item , $ new_item ) ) { goto NEXT_NEW_ITEM ; } } $ final_items [ ] = $ new_item ; $ next_symbol = $ new_item -> getExpected ( ) ; if ( ! $ next_symbol || $ next_symbol -> isTerminal ( ) ) { continue ; } $ name = $ next_symbol -> getName ( ) ; if ( isset ( $ known_next_symbols [ $ name ] ) ) { continue ; } $ next_symbols [ $ name ] = $ next_symbol ; NEXT_NEW_ITEM : } $ known_next_symbols += $ next_symbols ; $ new_items = [ ] ; foreach ( $ next_symbols as $ next_symbol ) { $ rules = $ grammar -> getRulesFor ( $ next_symbol ) ; foreach ( $ rules as $ rule ) { $ new_items [ ] = Item :: createFromRule ( $ rule ) ; } } } return new static ( $ final_items , $ items , $ grammar ) ; }
Create a Set from an Items using a grammar
@param Item[] $items Initial Items to expand
@param Grammar $grammar Grammar to expand non-terminals
@return static Returns new Set
@throws ConflictShiftReduceException Shift-reduce conflict is detected
@throws ConflictReduceReduceException Reduce-reduce conflict is detected
Create a Set from an Items using a grammar