package fastjson

import (
	
	
	
	
	
)

// Parser parses JSON.
//
// Parser may be re-used for subsequent parsing.
//
// Parser cannot be used from concurrent goroutines.
// Use per-goroutine parsers or ParserPool instead.
type Parser struct {
	// b contains working copy of the string to be parsed.
	b []byte

	// c is a cache for json values.
	c cache
}

// Parse parses s containing JSON.
//
// The returned value is valid until the next call to Parse*.
//
// Use Scanner if a stream of JSON values must be parsed.
func ( *Parser) ( string) (*Value, error) {
	 = skipWS()
	.b = append(.b[:0], ...)
	.c.reset()

	, ,  := parseValue(b2s(.b), &.c, 0)
	if  != nil {
		return nil, fmt.Errorf("cannot parse JSON: %s; unparsed tail: %q", , startEndString())
	}
	 = skipWS()
	if len() > 0 {
		return nil, fmt.Errorf("unexpected tail: %q", startEndString())
	}
	return , nil
}

// ParseBytes parses b containing JSON.
//
// The returned Value is valid until the next call to Parse*.
//
// Use Scanner if a stream of JSON values must be parsed.
func ( *Parser) ( []byte) (*Value, error) {
	return .Parse(b2s())
}

type cache struct {
	vs []Value
}

func ( *cache) () {
	.vs = .vs[:0]
}

func ( *cache) () *Value {
	if cap(.vs) > len(.vs) {
		.vs = .vs[:len(.vs)+1]
	} else {
		.vs = append(.vs, Value{})
	}
	// Do not reset the value, since the caller must properly init it.
	return &.vs[len(.vs)-1]
}

func ( string) string {
	if len() == 0 || [0] > 0x20 {
		// Fast path.
		return 
	}
	return skipWSSlow()
}

func ( string) string {
	if len() == 0 || [0] != 0x20 && [0] != 0x0A && [0] != 0x09 && [0] != 0x0D {
		return 
	}
	for  := 1;  < len(); ++ {
		if [] != 0x20 && [] != 0x0A && [] != 0x09 && [] != 0x0D {
			return [:]
		}
	}
	return ""
}

type kv struct {
	k string
	v *Value
}

// MaxDepth is the maximum depth for nested JSON.
const MaxDepth = 300

func ( string,  *cache,  int) (*Value, string, error) {
	if len() == 0 {
		return nil, , fmt.Errorf("cannot parse empty string")
	}
	++
	if  > MaxDepth {
		return nil, , fmt.Errorf("too big depth for the nested JSON; it exceeds %d", MaxDepth)
	}

	if [0] == '{' {
		, ,  := parseObject([1:], , )
		if  != nil {
			return nil, , fmt.Errorf("cannot parse object: %s", )
		}
		return , , nil
	}
	if [0] == '[' {
		, ,  := parseArray([1:], , )
		if  != nil {
			return nil, , fmt.Errorf("cannot parse array: %s", )
		}
		return , , nil
	}
	if [0] == '"' {
		, ,  := parseRawString([1:])
		if  != nil {
			return nil, , fmt.Errorf("cannot parse string: %s", )
		}
		 := .getValue()
		.t = typeRawString
		.s = 
		return , , nil
	}
	if [0] == 't' {
		if len() < len("true") || [:len("true")] != "true" {
			return nil, , fmt.Errorf("unexpected value found: %q", )
		}
		return valueTrue, [len("true"):], nil
	}
	if [0] == 'f' {
		if len() < len("false") || [:len("false")] != "false" {
			return nil, , fmt.Errorf("unexpected value found: %q", )
		}
		return valueFalse, [len("false"):], nil
	}
	if [0] == 'n' {
		if len() < len("null") || [:len("null")] != "null" {
			// Try parsing NaN
			if len() >= 3 && strings.EqualFold([:3], "nan") {
				 := .getValue()
				.t = TypeNumber
				.s = [:3]
				return , [3:], nil
			}
			return nil, , fmt.Errorf("unexpected value found: %q", )
		}
		return valueNull, [len("null"):], nil
	}

	, ,  := parseRawNumber()
	if  != nil {
		return nil, , fmt.Errorf("cannot parse number: %s", )
	}
	 := .getValue()
	.t = TypeNumber
	.s = 
	return , , nil
}

func ( string,  *cache,  int) (*Value, string, error) {
	 = skipWS()
	if len() == 0 {
		return nil, , fmt.Errorf("missing ']'")
	}

	if [0] == ']' {
		 := .getValue()
		.t = TypeArray
		.a = .a[:0]
		return , [1:], nil
	}

	 := .getValue()
	.t = TypeArray
	.a = .a[:0]
	for {
		var  *Value
		var  error

		 = skipWS()
		, ,  = parseValue(, , )
		if  != nil {
			return nil, , fmt.Errorf("cannot parse array value: %s", )
		}
		.a = append(.a, )

		 = skipWS()
		if len() == 0 {
			return nil, , fmt.Errorf("unexpected end of array")
		}
		if [0] == ',' {
			 = [1:]
			continue
		}
		if [0] == ']' {
			 = [1:]
			return , , nil
		}
		return nil, , fmt.Errorf("missing ',' after array value")
	}
}

func ( string,  *cache,  int) (*Value, string, error) {
	 = skipWS()
	if len() == 0 {
		return nil, , fmt.Errorf("missing '}'")
	}

	if [0] == '}' {
		 := .getValue()
		.t = TypeObject
		.o.reset()
		return , [1:], nil
	}

	 := .getValue()
	.t = TypeObject
	.o.reset()
	for {
		var  error
		 := .o.getKV()

		// Parse key.
		 = skipWS()
		if len() == 0 || [0] != '"' {
			return nil, , fmt.Errorf(`cannot find opening '"" for object key`)
		}
		.k, ,  = parseRawKey([1:])
		if  != nil {
			return nil, , fmt.Errorf("cannot parse object key: %s", )
		}
		 = skipWS()
		if len() == 0 || [0] != ':' {
			return nil, , fmt.Errorf("missing ':' after object key")
		}
		 = [1:]

		// Parse value
		 = skipWS()
		.v, ,  = parseValue(, , )
		if  != nil {
			return nil, , fmt.Errorf("cannot parse object value: %s", )
		}
		 = skipWS()
		if len() == 0 {
			return nil, , fmt.Errorf("unexpected end of object")
		}
		if [0] == ',' {
			 = [1:]
			continue
		}
		if [0] == '}' {
			return , [1:], nil
		}
		return nil, , fmt.Errorf("missing ',' after object value")
	}
}

func ( []byte,  string) []byte {
	if !hasSpecialChars() {
		// Fast path - nothing to escape.
		 = append(, '"')
		 = append(, ...)
		 = append(, '"')
		return 
	}

	// Slow path.
	return strconv.AppendQuote(, )
}

func ( string) bool {
	if strings.IndexByte(, '"') >= 0 || strings.IndexByte(, '\\') >= 0 {
		return true
	}
	for  := 0;  < len(); ++ {
		if [] < 0x20 {
			return true
		}
	}
	return false
}

func ( string) string {
	 := strings.IndexByte(, '\\')
	if  < 0 {
		// Fast path - nothing to unescape.
		return 
	}

	// Slow path - unescape string.
	 := s2b() // It is safe to do, since s points to a byte slice in Parser.b.
	 = [:]
	 = [+1:]
	for len() > 0 {
		 := [0]
		 = [1:]
		switch  {
		case '"':
			 = append(, '"')
		case '\\':
			 = append(, '\\')
		case '/':
			 = append(, '/')
		case 'b':
			 = append(, '\b')
		case 'f':
			 = append(, '\f')
		case 'n':
			 = append(, '\n')
		case 'r':
			 = append(, '\r')
		case 't':
			 = append(, '\t')
		case 'u':
			if len() < 4 {
				// Too short escape sequence. Just store it unchanged.
				 = append(, "\\u"...)
				break
			}
			 := [:4]
			,  := strconv.ParseUint(, 16, 16)
			if  != nil {
				// Invalid escape sequence. Just store it unchanged.
				 = append(, "\\u"...)
				break
			}
			 = [4:]
			if !utf16.IsSurrogate(rune()) {
				 = append(, string(rune())...)
				break
			}

			// Surrogate.
			// See https://en.wikipedia.org/wiki/Universal_Character_Set_characters#Surrogates
			if len() < 6 || [0] != '\\' || [1] != 'u' {
				 = append(, "\\u"...)
				 = append(, ...)
				break
			}
			,  := strconv.ParseUint([2:6], 16, 16)
			if  != nil {
				 = append(, "\\u"...)
				 = append(, ...)
				break
			}
			 := utf16.DecodeRune(rune(), rune())
			 = append(, string()...)
			 = [6:]
		default:
			// Unknown escape sequence. Just store it unchanged.
			 = append(, '\\', )
		}
		 = strings.IndexByte(, '\\')
		if  < 0 {
			 = append(, ...)
			break
		}
		 = append(, [:]...)
		 = [+1:]
	}
	return b2s()
}

// parseRawKey is similar to parseRawString, but is optimized
// for small-sized keys without escape sequences.
func ( string) (string, string, error) {
	for  := 0;  < len(); ++ {
		if [] == '"' {
			// Fast path.
			return [:], [+1:], nil
		}
		if [] == '\\' {
			// Slow path.
			return parseRawString()
		}
	}
	return , "", fmt.Errorf(`missing closing '"'`)
}

func ( string) (string, string, error) {
	 := strings.IndexByte(, '"')
	if  < 0 {
		return , "", fmt.Errorf(`missing closing '"'`)
	}
	if  == 0 || [-1] != '\\' {
		// Fast path. No escaped ".
		return [:], [+1:], nil
	}

	// Slow path - possible escaped " found.
	 := 
	for {
		 :=  - 1
		for  > 0 && [-1] == '\\' {
			--
		}
		if uint(-)%2 == 0 {
			return [:len()-len()+], [+1:], nil
		}
		 = [+1:]

		 = strings.IndexByte(, '"')
		if  < 0 {
			return , "", fmt.Errorf(`missing closing '"'`)
		}
		if  == 0 || [-1] != '\\' {
			return [:len()-len()+], [+1:], nil
		}
	}
}

func ( string) (string, string, error) {
	// The caller must ensure len(s) > 0

	// Find the end of the number.
	for  := 0;  < len(); ++ {
		 := []
		if ( >= '0' &&  <= '9') ||  == '.' ||  == '-' ||  == 'e' ||  == 'E' ||  == '+' {
			continue
		}
		if  == 0 ||  == 1 && ([0] == '-' || [0] == '+') {
			if len([:]) >= 3 {
				 := [ : +3]
				if strings.EqualFold(, "inf") || strings.EqualFold(, "nan") {
					return [:+3], [+3:], nil
				}
			}
			return "", , fmt.Errorf("unexpected char: %q", [:1])
		}
		 := [:]
		 = [:]
		return , , nil
	}
	return , "", nil
}

// Object represents JSON object.
//
// Object cannot be used from concurrent goroutines.
// Use per-goroutine parsers or ParserPool instead.
type Object struct {
	kvs           []kv
	keysUnescaped bool
}

func ( *Object) () {
	.kvs = .kvs[:0]
	.keysUnescaped = false
}

// MarshalTo appends marshaled o to dst and returns the result.
func ( *Object) ( []byte) []byte {
	 = append(, '{')
	for ,  := range .kvs {
		if .keysUnescaped {
			 = escapeString(, .k)
		} else {
			 = append(, '"')
			 = append(, .k...)
			 = append(, '"')
		}
		 = append(, ':')
		 = .v.MarshalTo()
		if  != len(.kvs)-1 {
			 = append(, ',')
		}
	}
	 = append(, '}')
	return 
}

// String returns string representation for the o.
//
// This function is for debugging purposes only. It isn't optimized for speed.
// See MarshalTo instead.
func ( *Object) () string {
	 := .MarshalTo(nil)
	// It is safe converting b to string without allocation, since b is no longer
	// reachable after this line.
	return b2s()
}

func ( *Object) () *kv {
	if cap(.kvs) > len(.kvs) {
		.kvs = .kvs[:len(.kvs)+1]
	} else {
		.kvs = append(.kvs, kv{})
	}
	return &.kvs[len(.kvs)-1]
}

func ( *Object) () {
	if .keysUnescaped {
		return
	}
	 := .kvs
	for  := range  {
		 := &[]
		.k = unescapeStringBestEffort(.k)
	}
	.keysUnescaped = true
}

// Len returns the number of items in the o.
func ( *Object) () int {
	return len(.kvs)
}

// Get returns the value for the given key in the o.
//
// Returns nil if the value for the given key isn't found.
//
// The returned value is valid until Parse is called on the Parser returned o.
func ( *Object) ( string) *Value {
	if !.keysUnescaped && strings.IndexByte(, '\\') < 0 {
		// Fast path - try searching for the key without object keys unescaping.
		for ,  := range .kvs {
			if .k ==  {
				return .v
			}
		}
	}

	// Slow path - unescape object keys.
	.unescapeKeys()

	for ,  := range .kvs {
		if .k ==  {
			return .v
		}
	}
	return nil
}

// Visit calls f for each item in the o in the original order
// of the parsed JSON.
//
// f cannot hold key and/or v after returning.
func ( *Object) ( func( []byte,  *Value)) {
	if  == nil {
		return
	}

	.unescapeKeys()

	for ,  := range .kvs {
		(s2b(.k), .v)
	}
}

// Value represents any JSON value.
//
// Call Type in order to determine the actual type of the JSON value.
//
// Value cannot be used from concurrent goroutines.
// Use per-goroutine parsers or ParserPool instead.
type Value struct {
	o Object
	a []*Value
	s string
	t Type
}

// MarshalTo appends marshaled v to dst and returns the result.
func ( *Value) ( []byte) []byte {
	switch .t {
	case typeRawString:
		 = append(, '"')
		 = append(, .s...)
		 = append(, '"')
		return 
	case TypeObject:
		return .o.MarshalTo()
	case TypeArray:
		 = append(, '[')
		for ,  := range .a {
			 = .()
			if  != len(.a)-1 {
				 = append(, ',')
			}
		}
		 = append(, ']')
		return 
	case TypeString:
		return escapeString(, .s)
	case TypeNumber:
		return append(, .s...)
	case TypeTrue:
		return append(, "true"...)
	case TypeFalse:
		return append(, "false"...)
	case TypeNull:
		return append(, "null"...)
	default:
		panic(fmt.Errorf("BUG: unexpected Value type: %d", .t))
	}
}

// String returns string representation of the v.
//
// The function is for debugging purposes only. It isn't optimized for speed.
// See MarshalTo instead.
//
// Don't confuse this function with StringBytes, which must be called
// for obtaining the underlying JSON string for the v.
func ( *Value) () string {
	 := .MarshalTo(nil)
	// It is safe converting b to string without allocation, since b is no longer
	// reachable after this line.
	return b2s()
}

// Type represents JSON type.
type Type int

const (
	// TypeNull is JSON null.
	TypeNull Type = 0

	// TypeObject is JSON object type.
	TypeObject Type = 1

	// TypeArray is JSON array type.
	TypeArray Type = 2

	// TypeString is JSON string type.
	TypeString Type = 3

	// TypeNumber is JSON number type.
	TypeNumber Type = 4

	// TypeTrue is JSON true.
	TypeTrue Type = 5

	// TypeFalse is JSON false.
	TypeFalse Type = 6

	typeRawString Type = 7
)

// String returns string representation of t.
func ( Type) () string {
	switch  {
	case TypeObject:
		return "object"
	case TypeArray:
		return "array"
	case TypeString:
		return "string"
	case TypeNumber:
		return "number"
	case TypeTrue:
		return "true"
	case TypeFalse:
		return "false"
	case TypeNull:
		return "null"

	// typeRawString is skipped intentionally,
	// since it shouldn't be visible to user.
	default:
		panic(fmt.Errorf("BUG: unknown Value type: %d", ))
	}
}

// Type returns the type of the v.
func ( *Value) () Type {
	if .t == typeRawString {
		.s = unescapeStringBestEffort(.s)
		.t = TypeString
	}
	return .t
}

// Exists returns true if the field exists for the given keys path.
//
// Array indexes may be represented as decimal numbers in keys.
func ( *Value) ( ...string) bool {
	 = .Get(...)
	return  != nil
}

// Get returns value by the given keys path.
//
// Array indexes may be represented as decimal numbers in keys.
//
// nil is returned for non-existing keys path.
//
// The returned value is valid until Parse is called on the Parser returned v.
func ( *Value) ( ...string) *Value {
	if  == nil {
		return nil
	}
	for ,  := range  {
		if .t == TypeObject {
			 = .o.Get()
			if  == nil {
				return nil
			}
		} else if .t == TypeArray {
			,  := strconv.Atoi()
			if  != nil ||  < 0 ||  >= len(.a) {
				return nil
			}
			 = .a[]
		} else {
			return nil
		}
	}
	return 
}

// GetObject returns object value by the given keys path.
//
// Array indexes may be represented as decimal numbers in keys.
//
// nil is returned for non-existing keys path or for invalid value type.
//
// The returned object is valid until Parse is called on the Parser returned v.
func ( *Value) ( ...string) *Object {
	 = .Get(...)
	if  == nil || .t != TypeObject {
		return nil
	}
	return &.o
}

// GetArray returns array value by the given keys path.
//
// Array indexes may be represented as decimal numbers in keys.
//
// nil is returned for non-existing keys path or for invalid value type.
//
// The returned array is valid until Parse is called on the Parser returned v.
func ( *Value) ( ...string) []*Value {
	 = .Get(...)
	if  == nil || .t != TypeArray {
		return nil
	}
	return .a
}

// GetFloat64 returns float64 value by the given keys path.
//
// Array indexes may be represented as decimal numbers in keys.
//
// 0 is returned for non-existing keys path or for invalid value type.
func ( *Value) ( ...string) float64 {
	 = .Get(...)
	if  == nil || .Type() != TypeNumber {
		return 0
	}
	return fastfloat.ParseBestEffort(.s)
}

// GetInt returns int value by the given keys path.
//
// Array indexes may be represented as decimal numbers in keys.
//
// 0 is returned for non-existing keys path or for invalid value type.
func ( *Value) ( ...string) int {
	 = .Get(...)
	if  == nil || .Type() != TypeNumber {
		return 0
	}
	 := fastfloat.ParseInt64BestEffort(.s)
	 := int()
	if int64() !=  {
		return 0
	}
	return 
}

// GetUint returns uint value by the given keys path.
//
// Array indexes may be represented as decimal numbers in keys.
//
// 0 is returned for non-existing keys path or for invalid value type.
func ( *Value) ( ...string) uint {
	 = .Get(...)
	if  == nil || .Type() != TypeNumber {
		return 0
	}
	 := fastfloat.ParseUint64BestEffort(.s)
	 := uint()
	if uint64() !=  {
		return 0
	}
	return 
}

// GetInt64 returns int64 value by the given keys path.
//
// Array indexes may be represented as decimal numbers in keys.
//
// 0 is returned for non-existing keys path or for invalid value type.
func ( *Value) ( ...string) int64 {
	 = .Get(...)
	if  == nil || .Type() != TypeNumber {
		return 0
	}
	return fastfloat.ParseInt64BestEffort(.s)
}

// GetUint64 returns uint64 value by the given keys path.
//
// Array indexes may be represented as decimal numbers in keys.
//
// 0 is returned for non-existing keys path or for invalid value type.
func ( *Value) ( ...string) uint64 {
	 = .Get(...)
	if  == nil || .Type() != TypeNumber {
		return 0
	}
	return fastfloat.ParseUint64BestEffort(.s)
}

// GetStringBytes returns string value by the given keys path.
//
// Array indexes may be represented as decimal numbers in keys.
//
// nil is returned for non-existing keys path or for invalid value type.
//
// The returned string is valid until Parse is called on the Parser returned v.
func ( *Value) ( ...string) []byte {
	 = .Get(...)
	if  == nil || .Type() != TypeString {
		return nil
	}
	return s2b(.s)
}

// GetBool returns bool value by the given keys path.
//
// Array indexes may be represented as decimal numbers in keys.
//
// false is returned for non-existing keys path or for invalid value type.
func ( *Value) ( ...string) bool {
	 = .Get(...)
	if  != nil && .t == TypeTrue {
		return true
	}
	return false
}

// Object returns the underlying JSON object for the v.
//
// The returned object is valid until Parse is called on the Parser returned v.
//
// Use GetObject if you don't need error handling.
func ( *Value) () (*Object, error) {
	if .t != TypeObject {
		return nil, fmt.Errorf("value doesn't contain object; it contains %s", .Type())
	}
	return &.o, nil
}

// Array returns the underlying JSON array for the v.
//
// The returned array is valid until Parse is called on the Parser returned v.
//
// Use GetArray if you don't need error handling.
func ( *Value) () ([]*Value, error) {
	if .t != TypeArray {
		return nil, fmt.Errorf("value doesn't contain array; it contains %s", .Type())
	}
	return .a, nil
}

// StringBytes returns the underlying JSON string for the v.
//
// The returned string is valid until Parse is called on the Parser returned v.
//
// Use GetStringBytes if you don't need error handling.
func ( *Value) () ([]byte, error) {
	if .Type() != TypeString {
		return nil, fmt.Errorf("value doesn't contain string; it contains %s", .Type())
	}
	return s2b(.s), nil
}

// Float64 returns the underlying JSON number for the v.
//
// Use GetFloat64 if you don't need error handling.
func ( *Value) () (float64, error) {
	if .Type() != TypeNumber {
		return 0, fmt.Errorf("value doesn't contain number; it contains %s", .Type())
	}
	return fastfloat.Parse(.s)
}

// Int returns the underlying JSON int for the v.
//
// Use GetInt if you don't need error handling.
func ( *Value) () (int, error) {
	if .Type() != TypeNumber {
		return 0, fmt.Errorf("value doesn't contain number; it contains %s", .Type())
	}
	,  := fastfloat.ParseInt64(.s)
	if  != nil {
		return 0, 
	}
	 := int()
	if int64() !=  {
		return 0, fmt.Errorf("number %q doesn't fit int", .s)
	}
	return , nil
}

// Uint returns the underlying JSON uint for the v.
//
// Use GetInt if you don't need error handling.
func ( *Value) () (uint, error) {
	if .Type() != TypeNumber {
		return 0, fmt.Errorf("value doesn't contain number; it contains %s", .Type())
	}
	,  := fastfloat.ParseUint64(.s)
	if  != nil {
		return 0, 
	}
	 := uint()
	if uint64() !=  {
		return 0, fmt.Errorf("number %q doesn't fit uint", .s)
	}
	return , nil
}

// Int64 returns the underlying JSON int64 for the v.
//
// Use GetInt64 if you don't need error handling.
func ( *Value) () (int64, error) {
	if .Type() != TypeNumber {
		return 0, fmt.Errorf("value doesn't contain number; it contains %s", .Type())
	}
	return fastfloat.ParseInt64(.s)
}

// Uint64 returns the underlying JSON uint64 for the v.
//
// Use GetInt64 if you don't need error handling.
func ( *Value) () (uint64, error) {
	if .Type() != TypeNumber {
		return 0, fmt.Errorf("value doesn't contain number; it contains %s", .Type())
	}
	return fastfloat.ParseUint64(.s)
}

// Bool returns the underlying JSON bool for the v.
//
// Use GetBool if you don't need error handling.
func ( *Value) () (bool, error) {
	if .t == TypeTrue {
		return true, nil
	}
	if .t == TypeFalse {
		return false, nil
	}
	return false, fmt.Errorf("value doesn't contain bool; it contains %s", .Type())
}

var (
	valueTrue  = &Value{t: TypeTrue}
	valueFalse = &Value{t: TypeFalse}
	valueNull  = &Value{t: TypeNull}
)