@Override
        public String toString() {
            if (fullPath != null) {
                return fullPath;
            }

            byte[] buf = new byte[16];
            int off = 0;

            int level = 0;
            Path[] items = new Path[4];
            for (Path p = this; p != null; p = p.parent) {
                if (items.length == level) {
                    items = Arrays.copyOf(items, items.length + 4);
                }
                items[level] = p;
                level++;
            }

            boolean ascii = true;

            for (int i = level - 1; i >= 0; i--) {
                Path item = items[i];
                String name = item.name;
                if (name == null) {
                    int intValue = item.index;
                    int intValueSize = IOUtils.stringSize(intValue);
                    while (off + intValueSize + 2 >= buf.length) {
                        int newCapacity = buf.length + (buf.length >> 1);
                        buf = Arrays.copyOf(buf, newCapacity);
                    }

                    buf[off++] = '[';
                    IOUtils.getChars(intValue, off + intValueSize, buf);
                    off += intValueSize;
                    buf[off++] = ']';
                } else {
                    if (off + 1 >= buf.length) {
                        int newCapacity = buf.length + (buf.length >> 1);
                        buf = Arrays.copyOf(buf, newCapacity);
                    }

                    if (i != level - 1) {
                        buf[off++] = '.';
                    }

                    if (JVM_VERSION == 8) {
                        char[] chars = getCharArray(name);
                        for (int j = 0; j < chars.length; j++) {
                            char ch = chars[j];
                            switch (ch) {
                                case '/':
                                case ':':
                                case ';':
                                case '`':
                                case '.':
                                case '~':
                                case '!':
                                case '@':
                                case '#':
                                case '%':
                                case '^':
                                case '&':
                                case '*':
                                case '[':
                                case ']':
                                case '<':
                                case '>':
                                case '?':
                                case '(':
                                case ')':
                                case '-':
                                case '+':
                                case '=':
                                case '\\':
                                case '"':
                                case '\'':
                                case ',':
                                    if (off + 1 >= buf.length) {
                                        int newCapacity = buf.length + (buf.length >> 1);
                                        buf = Arrays.copyOf(buf, newCapacity);
                                    }
                                    buf[off] = '\\';
                                    buf[off + 1] = (byte) ch;
                                    off += 2;
                                    break;
                                default:
                                    if ((ch >= 0x0001) && (ch <= 0x007F)) {
                                        if (off == buf.length) {
                                            int newCapacity = buf.length + (buf.length >> 1);
                                            buf = Arrays.copyOf(buf, newCapacity);
                                        }
                                        buf[off++] = (byte) ch;
                                    } else if (ch >= '\uD800' && ch < ('\uDFFF' + 1)) { //  //Character.isSurrogate(c)
                                        ascii = false;
                                        final int uc;
                                        if (ch < '\uDBFF' + 1) { // Character.isHighSurrogate(c)
                                            if (name.length() - i < 2) {
                                                uc = -1;
                                            } else {
                                                char d = name.charAt(i + 1);
                                                // d >= '\uDC00' && d < ('\uDFFF' + 1)
                                                if (d >= '\uDC00' && d < ('\uDFFF' + 1)) { // Character.isLowSurrogate(d)
                                                    uc = ((ch << 10) + d) + (0x010000 - ('\uD800' << 10) - '\uDC00'); // Character.toCodePoint(c, d)
                                                } else {
//                            throw new JSONException("encodeUTF8 error", new MalformedInputException(1));
                                                    buf[off++] = (byte) '?';
                                                    continue;
                                                }
                                            }
                                        } else {
                                            //
                                            // Character.isLowSurrogate(c)
                                            buf[off++] = (byte) '?';
                                            continue;
//                        throw new JSONException("encodeUTF8 error", new MalformedInputException(1));
                                        }

                                        if (uc < 0) {
                                            if (off == buf.length) {
                                                int newCapacity = buf.length + (buf.length >> 1);
                                                buf = Arrays.copyOf(buf, newCapacity);
                                            }
                                            buf[off++] = (byte) '?';
                                        } else {
                                            if (off + 3 >= buf.length) {
                                                int newCapacity = buf.length + (buf.length >> 1);
                                                buf = Arrays.copyOf(buf, newCapacity);
                                            }
                                            buf[off] = (byte) (0xf0 | ((uc >> 18)));
                                            buf[off + 1] = (byte) (0x80 | ((uc >> 12) & 0x3f));
                                            buf[off + 2] = (byte) (0x80 | ((uc >> 6) & 0x3f));
                                            buf[off + 3] = (byte) (0x80 | (uc & 0x3f));
                                            off += 4;
                                            j++; // 2 chars
                                        }
                                    } else if (ch > 0x07FF) {
                                        if (off + 2 >= buf.length) {
                                            int newCapacity = buf.length + (buf.length >> 1);
                                            buf = Arrays.copyOf(buf, newCapacity);
                                        }
                                        ascii = false;

                                        buf[off] = (byte) (0xE0 | ((ch >> 12) & 0x0F));
                                        buf[off + 1] = (byte) (0x80 | ((ch >> 6) & 0x3F));
                                        buf[off + 2] = (byte) (0x80 | ((ch) & 0x3F));
                                        off += 3;
                                    } else {
                                        if (off + 1 >= buf.length) {
                                            int newCapacity = buf.length + (buf.length >> 1);
                                            buf = Arrays.copyOf(buf, newCapacity);
                                        }
                                        ascii = false;

                                        buf[off] = (byte) (0xC0 | ((ch >> 6) & 0x1F));
                                        buf[off + 1] = (byte) (0x80 | ((ch) & 0x3F));
                                        off += 2;
                                    }
                                    break;
                            }
                        }
                    } else {
                        for (int j = 0; j < name.length(); j++) {
                            char ch = name.charAt(j);
                            switch (ch) {
                                case '/':
                                case ':':
                                case ';':
                                case '`':
                                case '.':
                                case '~':
                                case '!':
                                case '@':
                                case '#':
                                case '%':
                                case '^':
                                case '&':
                                case '*':
                                case '[':
                                case ']':
                                case '<':
                                case '>':
                                case '?':
                                case '(':
                                case ')':
                                case '-':
                                case '+':
                                case '=':
                                case '\\':
                                case '"':
                                case '\'':
                                case ',':
                                    if (off + 1 >= buf.length) {
                                        int newCapacity = buf.length + (buf.length >> 1);
                                        buf = Arrays.copyOf(buf, newCapacity);
                                    }
                                    buf[off] = '\\';
                                    buf[off + 1] = (byte) ch;
                                    off += 2;
                                    break;
                                default:
                                    if ((ch >= 0x0001) && (ch <= 0x007F)) {
                                        if (off == buf.length) {
                                            int newCapacity = buf.length + (buf.length >> 1);
                                            buf = Arrays.copyOf(buf, newCapacity);
                                        }
                                        buf[off++] = (byte) ch;
                                    } else if (ch >= '\uD800' && ch < ('\uDFFF' + 1)) { //  //Character.isSurrogate(c)
                                        ascii = false;
                                        final int uc;
                                        if (ch < '\uDBFF' + 1) { // Character.isHighSurrogate(c)
                                            if (name.length() - i < 2) {
                                                uc = -1;
                                            } else {
                                                char d = name.charAt(i + 1);
                                                // d >= '\uDC00' && d < ('\uDFFF' + 1)
                                                if (d >= '\uDC00' && d < ('\uDFFF' + 1)) { // Character.isLowSurrogate(d)
                                                    uc = ((ch << 10) + d) + (0x010000 - ('\uD800' << 10) - '\uDC00'); // Character.toCodePoint(c, d)
                                                } else {
//                            throw new JSONException("encodeUTF8 error", new MalformedInputException(1));
                                                    buf[off++] = (byte) '?';
                                                    continue;
                                                }
                                            }
                                        } else {
                                            //
                                            // Character.isLowSurrogate(c)
                                            buf[off++] = (byte) '?';
                                            continue;
//                        throw new JSONException("encodeUTF8 error", new MalformedInputException(1));
                                        }

                                        if (uc < 0) {
                                            if (off == buf.length) {
                                                int newCapacity = buf.length + (buf.length >> 1);
                                                buf = Arrays.copyOf(buf, newCapacity);
                                            }

                                            buf[off++] = (byte) '?';
                                        } else {
                                            if (off + 4 >= buf.length) {
                                                int newCapacity = buf.length + (buf.length >> 1);
                                                buf = Arrays.copyOf(buf, newCapacity);
                                            }

                                            buf[off] = (byte) (0xf0 | ((uc >> 18)));
                                            buf[off + 1] = (byte) (0x80 | ((uc >> 12) & 0x3f));
                                            buf[off + 2] = (byte) (0x80 | ((uc >> 6) & 0x3f));
                                            buf[off + 3] = (byte) (0x80 | (uc & 0x3f));
                                            off += 4;
                                            j++; // 2 chars
                                        }
                                    } else if (ch > 0x07FF) {
                                        if (off + 2 >= buf.length) {
                                            int newCapacity = buf.length + (buf.length >> 1);
                                            buf = Arrays.copyOf(buf, newCapacity);
                                        }
                                        ascii = false;

                                        buf[off] = (byte) (0xE0 | ((ch >> 12) & 0x0F));
                                        buf[off + 1] = (byte) (0x80 | ((ch >> 6) & 0x3F));
                                        buf[off + 2] = (byte) (0x80 | ((ch) & 0x3F));
                                        off += 3;
                                    } else {
                                        if (off + 1 >= buf.length) {
                                            int newCapacity = buf.length + (buf.length >> 1);
                                            buf = Arrays.copyOf(buf, newCapacity);
                                        }
                                        ascii = false;

                                        buf[off] = (byte) (0xC0 | ((ch >> 6) & 0x1F));
                                        buf[off + 1] = (byte) (0x80 | ((ch) & 0x3F));
                                        off += 2;
                                    }
                                    break;
                            }
                        }
                    }
                }
            }

            if (ascii) {
                if (STRING_CREATOR_JDK11 != null) {
                    byte[] bytes;
                    if (off == buf.length) {
                        bytes = buf;
                    } else {
                        bytes = new byte[off];
                        System.arraycopy(buf, 0, bytes, 0, off);
                    }
                    return fullPath = STRING_CREATOR_JDK11.apply(bytes, LATIN1);
                }

                if (STRING_CREATOR_JDK8 != null) {
                    char[] chars = new char[off];
                    for (int i = 0; i < off; i++) {
                        chars[i] = (char) buf[i];
                    }
                    return fullPath = STRING_CREATOR_JDK8.apply(chars, Boolean.TRUE);
                }
            }

            return fullPath = new String(buf, 0, off, ascii ? StandardCharsets.ISO_8859_1 : StandardCharsets.UTF_8);
        }
JSON formatting support using 4 spaces for indentation
@since 2.0.54
core/src/main/java/com/alibaba/fastjson2/JSONWriter.java