public function parse($marcspec)
    {
        if (!preg_match_all('/'.$this->MARCSPEC.'/', $marcspec, $this->parsed, PREG_SET_ORDER)) {
            throw new InvalidMARCspecException(
                InvalidMARCspecException::FS.
                InvalidMARCspecException::MISSINGFIELD,
                $marcspec
            );
        }

        $this->parsed = array_filter($this->parsed[0], 'strlen');

        if (!array_key_exists('field', $this->parsed)) { // TODO: check if 'tag' is the required key
            throw new InvalidMARCspecException(
                InvalidMARCspecException::FS.
                InvalidMARCspecException::FTAG,
                $marcspec
            );
        }

        if (strlen($this->parsed[0]) !== strlen($marcspec)) {
            throw new InvalidMARCspecException(
                InvalidMARCspecException::FS.
                InvalidMARCspecException::USELESS,
                $marcspec
            );
        }

        if (array_key_exists('charpos', $this->parsed)) {
            if (array_key_exists('indicatorpos', $this->parsed)) {
                throw new InvalidMARCspecException(
                    InvalidMARCspecException::FS.
                    InvalidMARCspecException::CHARORIND,
                    $marcspec
                );
            }

            if (array_key_exists('subfields', $this->parsed)) {
                throw new InvalidMARCspecException(
                    InvalidMARCspecException::FS.
                    InvalidMARCspecException::CHARORSF,
                    $marcspec
                );
            }
        }

        if (array_key_exists('subfields', $this->parsed)) {
            if (array_key_exists('indicatorpos', $this->parsed)) {
                throw new InvalidMARCspecException(
                    InvalidMARCspecException::FS.
                    InvalidMARCspecException::INDORSF,
                    $marcspec
                );
            }
        }

        if (array_key_exists('subspecs', $this->parsed)) {
            $_subSpecs = $this->matchSubSpecs($this->parsed['subspecs']);

            $this->parsed['subspecs'] = [];

            foreach ($_subSpecs as $subSpec) {
                if (1 < count($subSpec)) {
                    foreach ($subSpec as $orSubSpec) {
                        $_or[] = $this->matchSubTerms($orSubSpec);
                    }
                    $this->parsed['subspecs'][] = $_or; // TODO: Check if array is required since $_or is an array
                } else {
                    $this->parsed['subspecs'][] = $this->matchSubTerms($subSpec[0]);
                }
            }
        }
    }