Exemplo n.º 1
0
        /**
            * Writes a printable representation of this {@code Throwable}'s stack trace
            * to the specified print writer. If the {@code Throwable} contains a
            * {@link #getCause() cause}, the method will be invoked recursively for the
            * nested {@code Throwable}.
            *
            * @param err
            *            the writer to write the stack trace on.
            */
        public virtual void printStackTrace(java.io.PrintWriter err)
        {
            err.println(this.ToString());
            // Don't use getStackTrace() as it calls clone()
            // Get stackTrace, in case stackTrace is reassigned
            StackTraceElement[] stack = getInternalStackTrace();
            foreach (StackTraceElement element in stack) {
                err.println("\tat " + element);
            }

            StackTraceElement[] parentStack = stack;
            Throwable throwable = getCause();
            while (throwable != null) {
                err.print("Caused by: ");
                err.println(throwable);
                StackTraceElement[] currentStack = throwable.getInternalStackTrace();
                int duplicates = countDuplicates(currentStack, parentStack);
                for (int i = 0; i < currentStack.Length - duplicates; i++) {
                    err.println("\tat " + currentStack[i]);
                }
                if (duplicates > 0) {
                    err.println("\t... " + duplicates + " more");
                }
                parentStack = currentStack;
                throwable = throwable.getCause();
            }
        }
        /**
         * Implementation providing functionality for {@link #debugPrint} and for
         * {@link #verbosePrint}.  This prints the given map with nice line breaks.
         * If the debug flag is true, it additionally prints the type of the object
         * value.  If the contents of a map include the map itself, then the text
         * <em>(this Map)</em> is printed out.  If the contents include a
         * parent container of the map, the the text <em>(ancestor[i] Map)</em> is
         * printed, where i actually indicates the number of levels which must be
         * traversed in the sequential list of ancestors (e.g. father, grandfather,
         * great-grandfather, etc).
         *
         * @param out  the stream to print to
         * @param label  the label to be used, may be <code>null</code>.
         *  If <code>null</code>, the label is not output.
         *  It typically represents the name of the property in a bean or similar.
         * @param map  the map to print, may be <code>null</code>.
         *  If <code>null</code>, the text 'null' is output
         * @param lineage  a stack consisting of any maps in which the previous
         *  argument is contained. This is checked to avoid infinite recursion when
         *  printing the output
         * @param debug  flag indicating whether type names should be output.
         * @throws NullPointerException if the stream is <code>null</code>
         */
        private static void verbosePrintInternal(
            java.lang.PrintStream outJ,
            Object label,
            java.util.Map<Object, Object> map,
            ArrayStack lineage,
            bool debug)
        {
            printIndent(outJ, lineage.size());

            if (map == null)
            {
                if (label != null)
                {
                    outJ.print(label);
                    outJ.print(" = ");
                }
                outJ.println("null");
                return;
            }
            if (label != null)
            {
                outJ.print(label);
                outJ.println(" = ");
            }

            printIndent(outJ, lineage.size());
            outJ.println("{");

            lineage.push(map);

            for (java.util.Iterator<java.util.MapNS.Entry<Object, Object>> it = map.entrySet().iterator(); it.hasNext(); )
            {
                java.util.MapNS.Entry<Object, Object> entry = it.next();
                Object childKey = entry.getKey();
                Object childValue = entry.getValue();
                if (childValue is java.util.Map<Object, Object> && !lineage.contains(childValue))
                {
                    verbosePrintInternal(
                        outJ,
                        (childKey == null ? "null" : childKey),
                        (java.util.Map<Object, Object>)childValue,
                        lineage,
                        debug);
                }
                else
                {
                    printIndent(outJ, lineage.size());
                    outJ.print(childKey);
                    outJ.print(" = ");

                    int lineageIndex = lineage.indexOf(childValue);
                    if (lineageIndex == -1)
                    {
                        outJ.print(childValue);
                    }
                    else if (lineage.size() - 1 == lineageIndex)
                    {
                        outJ.print("(this Map)");
                    }
                    else
                    {
                        outJ.print(
                            "(ancestor["
                                + (lineage.size() - 1 - lineageIndex - 1)
                                + "] Map)");
                    }

                    if (debug && childValue != null)
                    {
                        outJ.print(' ');
                        outJ.println(childValue.getClass().getName());
                    }
                    else
                    {
                        outJ.println();
                    }
                }
            }

            lineage.pop();

            printIndent(outJ, lineage.size());
            outJ.println(debug ? "} " + map.getClass().getName() : "}");
        }