package com.mindprod.jprep;

/**
 * A stripped down version of StringBuilder that recycles the same StringBuilder object for building many Strings.
 * typical use: static final Quickfinal StringBuilder sb = new QuickStringBuilder( 1000 ); sb.append( "ab ); sb.append(
 * 'c' ); String s = toFinalString(); // "abc" // now clear for new problem sb.append( "de"), s = sb.toString(), //
 * "de", does not clear afterwards, we see the interim result. sb.append( "fg" ); s= sb.toString(); // "defg"
 * sb.clear(); You could do this all fairly easily on a StringBuilder object directly. I just wanted the toFinalString
 * convenience. The lazy allocation is just icing on the cake, to avoid wasting space for a QuickStringBuilder you
 * actually never use in a paricular run.
 *
 * @author Roedy Green of Canadian Mind Products copyright (c) 2005-2008
 */
final class QuickStringBuilder
    {
    /**
     * lazily allocated StringBuilder we use over and over for different tasks. Cannot be final.
     */
    private StringBuilder sb = null;

    /**
     * estimated length of the longest String we will build with this QuickStringBuilder object.
     */
    private final int estLength;

    // -------------------------- PUBLIC INSTANCE  METHODS --------------------------
    /**
     * append to what has already been built
     *
     * @param s string to append
     */
    public void append( String s )
        {
        if ( sb == null )
            {
            sb = new StringBuilder( estLength );
            }
        sb.append( s );
        }

    /**
     * append to what has already been built
     *
     * @param c char to append
     */
    public void append( char c )
        {
        if ( sb == null )
            {
            sb = new StringBuilder( estLength );
            }
        sb.append( c );
        }

    /**
     * logically clear the String being built, like setLength( 0 ) Does not internally result in allocating an new
     * storage or releasing any.
     */
    public void clear()
        {
        if ( this.sb != null )
            {
            sb.setLength( 0 );
            }
        }

    /**
     * Get length of string built so far
     *
     * @return length of string built so far
     */
    public int length()
        {
        if ( sb == null )
            {
            return 0;
            }
        else
            {
            return sb.length();
            }
        }

    /**
     * Like toString() followed by clear()
     *
     * @return completed string
     */
    public String toFinalString()
        {
        String s;
        if ( sb == null )
            {
            s = "";
            }
        else
            {
            s = sb.toString();
            }
        clear();
        return s;
        }

    /**
     * get interim string -- a normal StringBuilder.toString Does not clear the buffer. creates a copy of the string,
     * Does not, as in past, convert internal buffer to String and allocate a new buffer. Thus there is now no penalty
     * for an internal buffer much longer than the String finally created
     *
     * @return completed string
     */
    public String toString()
        {
        if ( sb == null )
            {
            return "";
            }
        else
            {
            return sb.toString();
            }
        }

    // --------------------------- CONSTRUCTORS ---------------------------

    /**
     * constructor
     *
     * @param length estimated max length of the generated strings. If you get in wrong, no problem, the internal buffer
     *               inside StringBuilder will automatically grow and stay grown for subsequent uses.
     */
    QuickStringBuilder( int length )
        {
        // use lazy allocation
        this.estLength = length;
        }
    }