skip to Main Content

I’m encountering an issue with System.Text.Json in C# related to the serialization of floating-point numbers. When serializing a float with a decimal part (e.g., 4.0), the library seems to omit the decimal part, resulting in the JSON representation being just 4 instead of 4.0.

I’ve tried using various configurations, including setting NumberHandling = JsonNumberHandling.AllowNamedFloatingPointLiterals and NumberHandling = JsonNumberHandling.WriteAsString, but the behavior remains the same.

Is there a way to preserve the complete representation (e.g., 4.0) during serialization, or is there a known limitation with the current version of System.Text.Json?

Thank you for any insights or suggestions.

2

Answers


  1. Chosen as BEST ANSWER

    Thank you for your comments,

    Here's how I fixed the problem:

    • Creating a Class :

      public class AddZerosToFloat : JsonConverter<float>
       {
           public AddZerosToFloat() { }
      
       public override float Read(
           ref Utf8JsonReader reader,
           Type typeToConvert,
           JsonSerializerOptions options)
       {
           throw new NotImplementedException("Unnecessary because CanRead is false. The type will skip the converter.");
       }
       public override bool CanConvert(Type objectType)
       {
           return objectType == typeof(float);
       }
       public override void Write(
           Utf8JsonWriter writer,
           float value,
           JsonSerializerOptions options)
       {
           if (Math.Truncate(value) == value)
           {
               writer.WriteRawValue(value.ToString("0.0", CultureInfo.InvariantCulture));
           }
           else
           {
               writer.WriteRawValue(value.ToString(CultureInfo.InvariantCulture));
      
      
          }
       }}
      
    • Add serializer option :

       string JsonString = JsonSerializer.Serialize(structClass, new JsonSerializerOptions 
       {
            ... other parameters
           Converters = { new AddZerosToFloat()}
       });
      

  2. JSON does not distinguish between float and int, it only has a concept of Number so in general you should avoid relying on the particular number formatting.

    If currently you can’t fix the app which uses the JSON you can use custom converter which will use specific number format. For example:

    class FloatConverter : JsonConverter<float>
    {
        public override float Read(ref Utf8JsonReader reader, Type typeToConvert, JsonSerializerOptions options) =>
            throw new NotImplementedException();
    
        public override void Write(Utf8JsonWriter writer, float value, JsonSerializerOptions options)
        {
            // at least one decimal place, add reasonable amount of places with #
            writer.WriteRawValue(value.ToString("0.0########", CultureInfo.InvariantCulture));
        }
    }
    

    And usage:

    var serialize = JsonSerializer.Serialize(new float[] { 1, 1.1f, 4.5555f }, new JsonSerializerOptions
    {
        Converters = { new FloatConverter() }
    });
    Console.WriteLine(serialize); // prints "[1.0,1.1,4.5555]"
    
    Login or Signup to reply.
Please signup or login to give your own answer.
Back To Top
Search