/*!
* @class RecordReader
*
* @headerfile <seqan/stream.h>
*
* @brief Buffer management when reading from @link StreamConcept streams
* @endlink.
*
* @signature template <typename TStream, typename TSpec> class RecordReader;
*
* @tparam TStream The @link StreamConcept @endlink to read from.
* @tparam TSpec The record reader specialization type.
*
* @section Examples
*
* @include demos/input_output/record_reader.cpp
*
* The output is as follows:
*
* @include demos/input_output/record_reader.cpp.stdout
*
*
*
* @mfn RecordReader#Position
*
* @brief Returns the position tpye to use in @link RecordReader#position
* @endlink and @link RecordReader#setPosition @endlink.
*
* @signature Position<TReader>::Type;
*
* @tparam TReader The RecordReader to query for its position type.
*
* @return Type The resulting position type.
*
* @see RecordReader#position
* @see RecordReader#setPosition
*
* @fn RecordReader::RecordReader
*
* @brief Constructor.
*
* @signature RecordReader::RecordReader();
* @signature RecordReader::RecordReader(stream[, bufferSize]);
*
* @param[in] stream The @link StreamConcept @endlink to read from.
* @param[in] bufferSize The size of the buffer to use. Type: <tt>unsigned</tt>.
*
* @fn RecordReader#resultCode
*
* @brief Return current status code of the reader/underlying stream.
*
* @signature int resultCode(reader);
*
* @param[in] reader The RecordReader to query for its status code.
*
* @return int The status code, 0 for no errors, non-0 value for errors.
*
* @fn RecordReader#value
*
* @brief Return the current value (character) of the reader.
*
* @signature char value(reader);
*
* @param[in] reader The RecordReader to read from.
*
* @return char The resulting character.
*
* This is undefined if the reader is at the end or an error occured.
*
* @fn RecordReader#goNext
*
* @brief Advance to the next position in the stream.
*
* @signature bool goNext(reader);
*
* @param[in,out] reader The RecordReader to advance.
*
* @return bool <tt>true</tt> on success, <tt>false</tt> on failure.
*
* @fn RecordReader#nextIs
*
* @brief Query whether the next record is of a given type.
*
* @signature bool nextIs(reader, tag)
*
* @param[in,out] reader The @link RecordReader @endlink to peek into. Remains
* unchanged.
* @param[in] tag Tag to select the given record type.
*
* @return bool Indicating whether the next record in <tt>reader</tt> is of type
* given by tag.
*
* @section Remarks
*
* The checks are mostly heuristic, mostly looking at one or few characters from
* reader.
*
* @fn RecordReader#atEnd
*
* @brief Returns <tt>true</tt> if there is no more data to be read.
*
* @signature bool atEnd(reader);
*
* @param[in] reader The @link RecordReader @endlink to query the state of.
*
* @return bool This function returns <tt>true</tt> if the file is at end or
* there was an error reading. It returns <tt>false</tt> if there
* is more data to read. In parsing functions, you can use @link
* RecordReader#resultCode @endlink to get the result to return
* from your parsing function.
*
* @see RecordReader#value
* @see RecordReader#resultCode
*
* @fn RecordReader#position
*
* @brief Returns the current position of the reader.
*
* @signature TPosition position(reader);
*
* @param[in] reader The RecordReader to query.
*
* @return TPosition The resulting position. Use @link RecordReader#Position
* @endlink to retrieve.
*
* @fn RecordReader#setPosition
*
* @brief Sets the current position of the reader.
*
* @signature void setPosition(reader, pos);
*
* @param[in,out] reader The RecordReader to set the position of.
* @param[in] pos The position to set.
*
* @section Remarks
*
* The underlying data source has to support setting the position. For
* RecordReader objects reading from strings this always works. When reading
* from streams, setting the position must be supported by the underlying stream
*
* @see RecordReader#position
*
* @fn RecordReader#readRecord
*
* @brief Reads one records (e.g. a single DNA sequence and its meta data) from
* a @link StreamConcept @endlink by the means of a @link RecordReader
* @endlink.
*
* @signature int readRecord(OUTPUT, reader, tag);
*
* @param[out] OUTPUT A format-specific value for one record, can also be
* multiple parameters.
* @param[in,out] reader A @link RecordReader @endlink to read from.
* @param[in] tag A format-specific tag.
*
* @return int A return code. 0 on success, non-0 value on error.
*
* @section Remarks
*
* If not noted otherwise, only a Single-Pass implementation is available for
* the given format.
*
* @fn RecordReader#read
*
* @brief Reads an entire document from a @link StreamConcept @endlink by the
* means of a @link RecordReader @endlink.
*
* @signature int read2(OUTPUT, reader, tag);
*
* @param[out] OUTPUT A format-specific value with records, can also be multiple
* parameters.
* @param[in,out] reader A @link RecordReader @endlink to read from.
* @param[in] tag A format-specific tag.
*
* @return int A return code. 0 on success, non-0 value on error.
*
* @section Remarks
*
* If not noted otherwise, only a Single-Pass implementation is available for
* the given format.
*
* @fn RecordReader#countLine
*
* @headerfile <seqan/stream.h>
*
* @brief Count characters in a line excluding <tt>'\r'</tt> and <tt>'\n'</tt>.
*
* @signature int countLine(num, reader);
*
* @param[in,out] num The <tt>unsigned</tt> to increment.
* @param[in,out] reader The @link RecordReader @endlink to read from.
*
* @return int 0 if there was no error on reading or non-0 if there were errors.
* A special value is @link TokenizeResult EOF_BEFORE_SUCCESS
* @endlink.
*
* @section Remarks
*
* This function stops on the beginning of the next line, if there is a next
* line (even though newline characters are not counted).
*
* Works on ANSI EOL and on Unix EOL.
*/