如何修复Go语言JSON校验代码中行尾错误的行号定位偏差
修复JSON语法错误位置检测的行号偏移问题
问题根源
原代码存在两个核心问题:
- 错误使用
decoder.InputOffset()获取位置:该值是解码器已成功读取的字节数,而非错误实际发生的位置。当行尾缺失逗号时,解码器会继续读取后续内容才触发错误,导致位置指向后续行。 - 行号列号计算逻辑未准确匹配错误偏移的归属行,对行尾位置的判断存在偏差。
修复后的代码
package main import ( "encoding/json" "fmt" "io" "strings" ) func main() { input := `{ "a": 1 "b": 2 }` decoder := json.NewDecoder(strings.NewReader(input)) decoder.UseNumber() var err error for { if _, err = decoder.Token(); err != nil { break } } if err != nil { if err == io.EOF { fmt.Println("JSON is valid") } else { // 断言错误为JSON语法错误,获取精确偏移量 syntaxErr, ok := err.(*json.SyntaxError) if !ok { fmt.Printf("JSON parsing error: %v\n", err) return } errorOffset := int(syntaxErr.Offset) jsonLines := strings.Split(input, "\n") currentOffset := 0 line := 1 character := 1 for _, lineContent := range jsonLines { lineLen := len(lineContent) // 判断错误偏移是否落在当前行范围内(包含行尾) if currentOffset+lineLen >= errorOffset { character = errorOffset - currentOffset + 1 // 列号从1开始计数 break } // 累加当前行长度+换行符(1字节) currentOffset += lineLen + 1 line++ } fmt.Printf("JSON is invalid at line %d, character %d: %v\n", line, character, syntaxErr) } } }
修复说明
- 获取精确错误偏移:将解析错误断言为
*json.SyntaxError,直接使用其Offset字段,该值是JSON规范定义的错误发生精确位置,而非解码器已读取的滞后位置。 - 修正行号列号计算:逐行累加字节偏移量,判断错误偏移是否属于当前行内容范围(从当前行起始偏移到行尾)。如果是,直接计算列号;否则进入下一行。这种逻辑能准确将行尾缺失逗号的错误归属到错误实际发生的行,而非后续行。
内容的提问来源于stack exchange,提问作者rubypoe
相关产品推荐
相关产品推荐

