protected function checkGrammar(array $nodes)
    {
        // TODO Make sure that separators are only in the child nodes of the array node of a function node
        // (If this happens the calculator will throw an exception)

        foreach ($nodes as $index => $node) {
            if (is_a($node, SymbolNode::class)) {
                /** @var $node SymbolNode */

                $symbol = $node->getSymbol();

                if (is_a($symbol, AbstractOperator::class)) {
                    /** @var $symbol AbstractOperator */

                    $posOfRightOperand = $index + 1;

                    // Make sure the operator is positioned left of a (potential) operand (=prefix notation).
                    // Example term: "-1"
                    if ($posOfRightOperand >= sizeof($nodes)) {
                        $this->throwException(
                            ParserException::class,
                            'Error: Found operator that does not stand before an operand.',
                            $node->getToken()->getValue(),
                            $node->getToken()->getPosition()
                        );
                    }

                    $posOfLeftOperand = $index - 1;

                    $leftOperand = null;

                    // Operator is unary if positioned at the beginning of a term
                    if ($posOfLeftOperand >= 0) {
                        $leftOperand = $nodes[$posOfLeftOperand];

                        if (is_a($leftOperand, SymbolNode::class)) {
                            /** @var $leftOperand SymbolNode */
                            if (is_a($leftOperand->getSymbol(), AbstractOperator::class)
                                ||
                                is_a($leftOperand->getSymbol(), AbstractSeparator::class)
                            ) {
                                // Operator is unary if positioned right to another operator
                                $leftOperand = null;
                            }
                        }
                    }

                    // If null, the operator is unary
                    if ($leftOperand === null) {
                        if (! $symbol->getOperatesUnary()) {
                            $this->throwException(
                                ParserException::class,
                                'Error: Found operator in unary notation that is not unary.',
                                $node->getToken()->getValue(),
                                $node->getToken()->getPosition()
                            );
                        }

                        // Remember that this node represents a unary operator
                        $node->setIsUnaryOperator(true);
                    } else {
                        if (! $symbol->getOperatesBinary()) {
                            $this->throwException(
                                ParserException::class,
                                'Error: Found operator in binary notation that is not binary.',
                                $node->getToken()->getValue(),
                                $node->getToken()->getPosition()
                            );
                        }
                    }
                }
            } else {
                /** @var $node ContainerNode */
                $this->checkGrammar($node->getChildNodes());
            }
        }

        if ($this->customGrammarChecker !== null) {
            $customGrammarChecker = $this->customGrammarChecker;

            // Execute custom grammar checker function
            $customGrammarChecker($nodes);
        }
    }