/**
         * Notifies this evaluation tracker that the evaluation of the specified
         * cell Is complete. <p/>
         *
         * Every successful call to <tt>startEvaluate</tt> must be followed by a
         * call to <tt>endEvaluate</tt> (recommended in a finally block) to enable
         * proper tracking of which cells are being evaluated at any point in time.<p/>
         *
         * Assuming a well behaved client, parameters to this method would not be
         * required. However, they have been included to assert correct behaviour,
         * and form more meaningful error messages.
         */
        public void EndEvaluate(HSSFWorkbook workbook, HSSFSheet sheet, int srcRowNum, int srcColNum)
        {
            int nFrames = _evaluationFrames.Count;
            if (nFrames < 1)
            {
                throw new InvalidOperationException("Call to endEvaluate without matching call to startEvaluate");
            }

            nFrames--;
            CellEvaluationFrame cefExpected = (CellEvaluationFrame)_evaluationFrames[nFrames];
            CellEvaluationFrame cefActual = new CellEvaluationFrame(workbook, sheet, srcRowNum, srcColNum);
            if (!cefActual.Equals(cefExpected))
            {
                throw new Exception("Wrong cell specified. "
                        + "Corresponding startEvaluate() call was for cell {"
                        + cefExpected.FormatAsString() + "} this endEvaluate() call Is for cell {"
                        + cefActual.FormatAsString() + "}");
            }
            // else - no problems so pop current frame
            _evaluationFrames.Remove(nFrames);
        }
        /**
         * Notifies this evaluation tracker that the evaluation of the specified
         * cell Is complete. <p/>
         *
         * Every successful call to <c>startEvaluate</c> must be followed by a
         * call to <c>endEvaluate</c> (recommended in a finally block) to enable
         * proper tracking of which cells are being evaluated at any point in time.<p/>
         *
         * Assuming a well behaved client, parameters to this method would not be
         * required. However, they have been included to assert correct behaviour,
         * and form more meaningful error messages.
         */
        public void EndEvaluate(HSSFWorkbook workbook, HSSFSheet sheet, int srcRowNum, int srcColNum)
        {
            int nFrames = _evaluationFrames.Count;

            if (nFrames < 1)
            {
                throw new InvalidOperationException("Call to endEvaluate without matching call to startEvaluate");
            }

            nFrames--;
            CellEvaluationFrame cefExpected = (CellEvaluationFrame)_evaluationFrames[nFrames];
            CellEvaluationFrame cefActual   = new CellEvaluationFrame(workbook, sheet, srcRowNum, srcColNum);

            if (!cefActual.Equals(cefExpected))
            {
                throw new Exception("Wrong cell specified. "
                                    + "Corresponding startEvaluate() call was for cell {"
                                    + cefExpected.FormatAsString() + "} this endEvaluate() call Is for cell {"
                                    + cefActual.FormatAsString() + "}");
            }
            // else - no problems so pop current frame
            _evaluationFrames.Remove(nFrames);
        }