Note that there are some explanatory texts on larger screens.

plurals
  1. PO
    text
    copied!<p>Your condition in the while loop is wrong. <code>ios::eof()</code> isn't predictive; it will only be set once the stream has attempted (internally) to read beyond end of file. You have to check after each<br> input.</p> <p>The classical way of handling your case would be to define a <code>&gt;&gt;</code> function for <code>GTable</code>, along the lines of:</p> <pre><code>std::istream&amp; operator&gt;&gt;( std::istream&amp; source, GTable&amp; dest ) { std::string line; while ( std::getline( source, line ) &amp;&amp; line.empty() ) { } if ( source ) { std::istringstream tmp( line ); std::string name; int count; if ( !(tmp &gt;&gt; name &gt;&gt; count) ) { source.setstate( std::ios::failbit ); } else { std::vector&lt; char &gt; adjactentOnes; char ch; while ( tmp &gt;&gt; ch ) { adjactentOnes.push_back( ch ); } if ( !tmp.eof() || adjactentOnes.size() != count ) { source.setstate( std::ios::failbit ); } else { dest.Name = name; dest.Out = count; for ( int i = 0; i &lt; count; ++ i ) { dest.AdjacentOnes.addFront( adjactentOnes[ i ] ); } } } } return source; } </code></pre> <p>(This was written rather hastily. In real code, I'd almost certainly factor the inner loop out into a separate function.)</p> <p>Note that:</p> <ul> <li><p>We read line by line, in order to verify the format (and to allow resynchronization in case of error).</p></li> <li><p>We set <code>failbit</code> in the source stream in case of an input error.</p></li> <li><p>We skip empty lines (since your input apparently contains them).</p></li> <li><p>We do not modify the target element until we are sure that the input is correct.</p></li> </ul> <p>One we have this, it is easy to loop over all of the elements:</p> <pre><code>int slot = 0; while ( slot &lt; GTable.size() &amp;&amp; fin &gt;&gt; GTable[ slot ] ) { ++ slot; } if ( slot != GTable.size ) // ... error ... </code></pre> <p>EDIT:</p> <p>I'll point this out explicitly, because the other people responding seem to have missed it: it is absolutely imperative to ensure that you have the place to read into <strong>before</strong> attempting the read.</p> <p>EDIT 2:</p> <p>Given the number of wrong answers this question is receiving, I would like to stress:</p> <ul> <li><p>Any use of <code>fin.eof()</code> <strong>before</strong> the input is known to fail is wrong.</p></li> <li><p>Any use of <code>fin.good()</code>, period, is wrong.</p></li> <li><p>Any use of one of the values read before having tested that the input has succeeded is wrong. (This doesn't prevent things like <code>fin &gt;&gt; a &gt;&gt; b</code>, as long as neither <code>a</code> or <code>b</code> are used before the success is tested.)</p></li> <li><p>Any attempt to read into <code>Gtable[slot]</code> without ensuring that <code>slot</code> is in bounds is wrong.</p></li> </ul> <p>With regards to <code>eof()</code> and <code>good()</code>:</p> <p>The base class of <code>istream</code> and <code>ostream</code> defines three &ldquo;error&rdquo; bits: <code>failbit</code>, <code>badbit</code> and <code>eofbit</code>. It's important to understand when these are set: <code>badbit</code> is set in case of a non-recoverable hardward error (practically never, in fact, since most implementations can't or don't detect such errors); and <code>failbit</code> is set in any other case the input fails&mdash;either no data available (end of file), or a format error (<code>"abc"</code> when inputting an int, etc.). <code>eofbit</code> is set <strong>anytime</strong> the <code>streambuf</code> returns <code>EOF</code>, whether this causes the input to fail or not! Thus, if you read an <code>int</code>, and the stream contains <code>"123"</code>, without trailing white space or newline, <code>eofbit</code> will be set (since the stream must read ahead to know where the <code>int</code> ends); if the stream contains <code>"123\n"</code>, <code>eofbit</code> will not be set. In both cases, however, the input succeeds, and <code>failbit</code> will not be set.</p> <p>To read these bits, there are the following functions (as code, since I don't know how to get a table otherwise):</p> <pre><code>eof(): returns eofbit bad(): returns badbit fail(): returns failbit || badbit good(): returns !failbit &amp;&amp; !badbit &amp;&amp; !eofbit operator!(): returns fail() operator void*(): returns fail() ? NULL : this (typically---all that's guaranteed is that !fail() returns non-null.) </code></pre> <p>Given this: the first check must always be <code>fail()</code> or one of the <code>operator</code> (which are based on <code>fail</code>). Once <code>fail()</code> returns true, we can use the other functions to determine why:</p> <pre><code>if ( fin.bad() ) { // Serious problem, disk read error or such. } else if ( fin.eof() ) { // End of file: there was no data there to read. } else { // Formatting error: something like "abc" for an int } </code></pre> <p>Practically speaking, any other use is an error (and any use of <code>good()</code> is an error&mdash;don't ask me why the function is there).</p>
 

Querying!

 
Guidance

SQuiL has stopped working due to an internal error.

If you are curious you may find further information in the browser console, which is accessible through the devtools (F12).

Reload