001////////////////////////////////////////////////////////////////////////////////
002// checkstyle: Checks Java source code for adherence to a set of rules.
003// Copyright (C) 2001-2014  Oliver Burn
004//
005// This library is free software; you can redistribute it and/or
006// modify it under the terms of the GNU Lesser General Public
007// License as published by the Free Software Foundation; either
008// version 2.1 of the License, or (at your option) any later version.
009//
010// This library is distributed in the hope that it will be useful,
011// but WITHOUT ANY WARRANTY; without even the implied warranty of
012// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
013// Lesser General Public License for more details.
014//
015// You should have received a copy of the GNU Lesser General Public
016// License along with this library; if not, write to the Free Software
017// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
018////////////////////////////////////////////////////////////////////////////////
019package com.puppycrawl.tools.checkstyle.api;
020
021import com.google.common.collect.Lists;
022import java.util.Iterator;
023import java.util.List;
024
025/**
026 * Simple implementation of a LIFO Stack that can be used instead of
027 * {@link java.util.Vector} which is <tt>synchronized</tt>.
028 * @author oliverb
029 * @param <E> The type to hold.
030 */
031public class FastStack<E> implements Iterable<E>
032{
033    /** Hold the entries in the stack. */
034    private final List<E> entries = Lists.newArrayList();
035
036    /**
037     * Pushes the supplied element onto the stack.
038     * @param element the element to push onto the stack.
039     */
040    public void push(E element)
041    {
042        entries.add(element);
043    }
044
045    /**
046     * Returns whether the stack is empty.
047     * @return whether the stack is empty.
048     */
049    public boolean isEmpty()
050    {
051        return entries.isEmpty();
052    }
053
054    /**
055     * Returns the number of entries in the stack.
056     * @return the number of entries in the stack.
057     */
058    public int size()
059    {
060        return entries.size();
061    }
062
063    /**
064     * Returns the entry at the top of the stack without removing it.
065     * @return the top entry
066     * @throws IllegalStateException if the stack is empty.
067     */
068    public E peek()
069    {
070        if (entries.isEmpty()) {
071            throw new IllegalStateException("FastStack is empty");
072        }
073        return entries.get(entries.size() - 1);
074    }
075
076    /**
077     * Returns the entry at the top of the stack by removing it.
078     * @return the top entry
079     * @throws IllegalStateException if the stack is empty.
080     */
081    public E pop()
082    {
083        if (entries.isEmpty()) {
084            throw new IllegalStateException("FastStack is empty");
085        }
086        return entries.remove(entries.size() - 1);
087    }
088
089    /**
090     * Return the element at the specified index. It does not remove the
091     * element from the stack.
092     * @param index the index to return
093     * @return the element at the index
094     * @throws IllegalArgumentException if index out of range
095     */
096    public E peek(int index)
097    {
098        if ((index < 0) || (index >= entries.size())) {
099            throw new IllegalArgumentException("index out of range.");
100        }
101        return entries.get(index);
102    }
103
104    /**
105     * Returns if the stack contains the specified element.
106     * @param element the element to find
107     * @return whether the stack contains the entry
108     */
109    public boolean contains(E element)
110    {
111        return entries.contains(element);
112    }
113
114    /**
115     * Clears the stack.
116     */
117    public void clear()
118    {
119        entries.clear();
120    }
121
122    /**
123     * Returns an iterator that goes from the oldest element to the newest.
124     * @return an iterator
125     */
126    @Override
127    public Iterator<E> iterator()
128    {
129        return entries.iterator();
130    }
131
132    /**
133     * Factory method to create a new instance.
134     * @param <T> the type of elements to hold in the stack.
135     * @return a new instance of {@link FastStack}
136     */
137    public static <T> FastStack<T> newInstance()
138    {
139        return new FastStack<T>();
140    }
141}