简体   繁体   中英

Defining a C# class that varies sometimes between int and a dictionary

using System.Web.Script.Serialization;

public class AfValue
{
    public DateTime timeStamp { get; set; }
    public int value { get; set; }
}

public class AfValues
{
    public List<AfValue> items { get; set; }
}

I defined my class above and I get data that looks like the one below and I'm having a problem. How do I handle that part in the middle of the data? For the most part the Value is an integer; however, sometimes it is a dictionary and I want to get the Value in the dictionary.

{
  "Items": [
    {
      "Timestamp": "2018-08-30T02:23:55.3390808Z",
      "Value": 16
    },
    {
      "Timestamp": "2018-08-30T02:31:22.0117492Z",
      "Value": 1
    },
    {
      "Timestamp": "2018-08-30T02:32:07.9333343Z",
      "Value": 16
    },
    {
      "Timestamp": "2018-08-30T02:34:15.0780029Z",
      "Value": {
        "Name": "Bad Input",
        "Value": 255,
        "IsSystem": true
      }
    },
    {
      "Timestamp": "2018-08-30T02:41:52.4217834Z",
      "Value": 16
    },
    {
      "Timestamp": "2018-08-30T02:41:56.4251708Z",
      "Value": 8
    },
    {
      "Timestamp": "2018-08-30T02:42:06.6542053Z",
      "Value": 24
    }
  ]
}

Edit: I am not sure if this is the same as the other problem. I can't map that solution to my problem.

Also, I can't use JSON.net. We have to use System.Web.Script.Serialization.

You can use Json.NET which has JsonConverter , declare Value as a class with three properties, for integers just read the integer and convert it to a Value instance with setting it's relevant property.

There is an example in the linked documentation, pay attention to ReadJson method which does the conversion from string to Version :

public override Version ReadJson(JsonReader reader, Type objectType, Version existingValue, bool hasExistingValue, JsonSerializer serializer)
{
    string s = (string)reader.Value;

    return new Version(s);
}

What you need to do is get reader.Value , check if it's a single integer or an object and return an instance of the class you created for the Value .

It looks like you are trying to mimic OSIsoft's AFValue and AFValues, including the SYSTEM State Set which has "Bad Value" among other. A couple of things to note.

  • In OSIsoft's AF SDK, the AFValue .Value property is an object, which is why it can be a variety of different things.
  • Also in the AF SDK, AFValues implements List rather than it within a property.
  • While you may think of it as a dictionary, the SYSTEM state set is actually more of an enumeration.

Others here will focus on your stated problem, but keep in mind that an AFValue can be Int16, Int32, Int64, Single, Double, String, DateTime, an enumeration value, or other things. Particularly in the process controls world, I would tend to see Single or Double as they represent measurements coming from sensors, more so than an integer.

Though you seem to be using PI Web API, I would encourage to check out the Live Library for Help on AF SDK. You may also want to see help for PI Web API Reference.

You may want to investigate the PI Web API Client Library for DotNet on GitHub. It already has done much of the heavy lifting for you.

Finally, I know you have an account on PI Square, so this type of question is more than welcome in PI Developers Club .

Rick Davin from OSIsoft

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM