public function parse(array &$argv=null)
    {
        $this->_options = array();

        if ($argv === null) {
            if (isset($_SERVER['argv'])) {
                $argv = $_SERVER['argv'];
            } else {
                $argv = array();
            }
        }

        $this->_programName = array_shift($argv);

        for ($i = 0; $i < count($argv); $i++) {
            if (preg_match('/^(--?)([a-z][a-z\-]*)(?:=(.+)?)?$/i', $argv[$i], $matches)) {
                if (isset($matches[3])) {
                    # put parameter back on stack of arguments
                    array_splice($argv, $i, 1, $matches[3]);
                    $paramGiven = true;
                } else {
                    # throw away the flag
                    array_splice($argv, $i, 1);
                    $paramGiven = false;
                }

                $flag = $matches[2];
                if ($this->_config & self::CONF_IGNORECASE) {
                    $flag = strtolower($flag);
                }

                if ($matches[1] == '--') {
                    # long flag
                    $this->parseOption($flag, $argv, $i, $paramGiven);
                } else {
                    # short flag
                    foreach (str_split($flag) as $shortFlag) {
                        $this->parseOption($shortFlag, $argv, $i, $paramGiven);
                    }
                }

                # decrement the index for the flag that was taken
                $i--;
            } elseif ($argv[$i] == '--') {
                if ($this->_config & self::CONF_DASHDASH) {
                    # stop processing arguments
                    break;
                }
            }
        }

        return $argv;
    }