Страницы

Поиск по вопросам

воскресенье, 15 декабря 2019 г.

Как перевести `VB.NET` код c лямбда-выражениями в код с циклами

#net #vbnet #сериализация #jsonnet


Проект под .NET 3.5 в Visual Studio 2008, это продолжение этого вопроса про сериализацию/десериализацию
и динамически меняющиеся свойства JSON.

В этом ответе имеется решение вопроса несовместимости форматов сериализаторов, которое
состоит в том что по умолчанию Newtonsoft.Json сохраняет публичные свойства в JSON,
а DataContractJsonSerializer сохраняет приватные свойства. Соответственно сериализация
одного и того же объекта дает разный результат.

Для DataContractJsonSerializer

{
  "ExProperty": {
    "_disabled": false,
    "_el_class": null,
    "_enum_values": [],
    "_id": "124",
    "_inline_script": null,
    "_inline_style": null,
    "_innerHTML": null,
    "_input_max": 0,
    "_input_min": 0,
    "_input_min_zero": false,
    "_input_subtype": null,
    "_nolabel": true,
    "_onclick": null,
    "_order": 0,
    "_parent_wrapp_class": "rrrrrrr",
    "_placeholder": null,
    "_value": null,
    "_width": 0,
    "_wrapp_class": null,
    "_wrapp_col_md": 55,
    "_wrapp_label_class": "eeee",
    "_dt_append": null,
    "_dt_append_name": null,
    "_dt_name": null,
    "_fieldSet": [
      "qqqqqqqqqqqqq",
      "aaaaaaaaaaa",
      "ssssssssssssss",
      "dddddddddddddd",
      "fgfffffffffffffffffff"
    ],
    "_fieldset_name": "aaaaaaaaaaa",
    "_isfiltr": false,
    "_lbl": null,
    "_lbl_short": null,
    "_lkp_filter": null,
    "_lkp_idas": null,
    "_lkp_nameas": null,
    "_lkp_table": null,
    "_req": false,
    "_sh_in_add": false,
    "_sh_in_edit": false,
    "_sh_in_list": false,
    "_type": null
  },
  "PropertyOne": "значение 1",
  "PropertyThree": null,
  "PropertyTwo": "значение 2"
}


Для Newtonsoft.Json

{
  "PropertyOne": "значение 1",
  "PropertyTwo": "значение 2",
  "PropertyThree": null,
  "ExProperty": {
    "fieldSets": [
      "qqqqqqqqqqqqq",
      "aaaaaaaaaaa",
      "ssssssssssssss",
      "dddddddddddddd",
      "fgfffffffffffffffffff"
    ],
    "fieldset_name": "aaaaaaaaaaa",
    "lbl": null,
    "lbl_short": null,
    "type": 0,
    "req": false,
    "lkp_table": null,
    "lkp_nameas": null,
    "lkp_idas": null,
    "lkp_filter": null,
    "dt_name": null,
    "dt_append_name": null,
    "dt_append": null,
    "sh_in_edit": false,
    "sh_in_add": false,
    "sh_in_list": false,
    "isfiltr": false,
    "order": 0,
    "wrapp_col_md": 55,
    "parent_wrapp_class": "rrrrrrr",
    "wrapp_class": null,
    "wrapp_label_class": "eeee",
    "el_class": null,
    "value": null,
    "innerHTML": null,
    "placeholder": null,
    "nolabel": true,
    "width": 0,
    "onClick": null,
    "inlineStyle": null,
    "Disabled": false,
    "Id": "124",
    "inlineScript": null,
    "inputSubtype": null,
    "InputMinZero": false,
    "inputMin": 0,
    "inputMax": 0,
    "EnumValues": []
  }
}


Требуется переписать класс из ответа, так чтобы он компилировался в 2008 студии.

Imports System.Reflection
Imports Newtonsoft.Json
Imports Newtonsoft.Json.Serialization

Public Class MyContractResolver
    Inherits DefaultContractResolver
    Protected Overrides Function CreateProperties(type As Type, memberSerialization
As MemberSerialization) As IList(Of JsonProperty)
        Dim props = type.GetProperties(BindingFlags.Public Or BindingFlags.NonPublic
Or BindingFlags.Instance).
                            Select(Function(p) MyBase.CreateProperty(p, memberSerialization)).
                            Union(type.GetFields(BindingFlags.Public Or BindingFlags.NonPublic
Or BindingFlags.Instance).
                            Select(Function(f) MyBase.CreateProperty(f, memberSerialization))).ToList()

        props.ForEach(Sub(p)
                          p.Writable = True
                          p.Readable = True
                      End Sub)
        Return props
    End Function
End Class


Сейчас код не воспринимается, ибо нет таких конструкций в 2008 версии.


    


Ответы

Ответ 1



Попробуйте такой вариант, должно сработать: Imports System.Reflection Imports Newtonsoft.Json Imports Newtonsoft.Json.Serialization Public Class MyContractResolver Inherits DefaultContractResolver Protected Overrides Function CreateProperties(ByVal type As Type, ByVal memberSerialization As MemberSerialization) As IList(Of JsonProperty) Dim props As New List(Of JsonProperty)() Dim propsInfo As PropertyInfo() = type.GetProperties(BindingFlags.Public Or BindingFlags.NonPublic Or BindingFlags.Instance) For Each pi As PropertyInfo In propsInfo Dim jp = MyBase.CreateProperty(pi, memberSerialization) If Not props.Contains(jp) Then props.Add(jp) End If Next Dim fieldsInfo As FieldInfo() = type.GetFields(BindingFlags.Public Or BindingFlags.NonPublic Or BindingFlags.Instance) For Each pi As FieldInfo In fieldsInfo Dim jp = MyBase.CreateProperty(pi, memberSerialization) If Not props.Contains(jp) Then props.Add(jp) End If Next For Each p As JsonProperty In props p.Writable = True p.Readable = True Next Return props End Function End Class

Ответ 2



Видимо, VB2008 ещё не понимал многострочные лямбды, поэтому соответствующую функцию можно сделать обычной, либо просто сделать обход списка циклом: For Each p In props p.Writable = True p.Readable = True Next p

Комментариев нет:

Отправить комментарий